HEAD+fixes
@ -14,3 +14,4 @@ dist
|
||||
OpenLP.egg-info
|
||||
build
|
||||
resources/innosetup/Output
|
||||
_eric4project
|
||||
|
@ -1,58 +0,0 @@
|
||||
This content can be found at this URL:
|
||||
http://netsuperbrain.com/Postmodern%20PostgreSQL%20Application%20Development.pdf
|
||||
|
||||
Page 11-15: QtDesigner
|
||||
Page 18-20: SQLAlchemy
|
||||
Page 21-23: PyQt - widget
|
||||
Page 24 : main
|
||||
Page 28 : py2exe and release
|
||||
|
||||
|
||||
==============================
|
||||
This is the destilled content.
|
||||
==============================
|
||||
|
||||
----------------
|
||||
** sqlalchemy **
|
||||
----------------
|
||||
from sqlalchemy import create_engine, MetaData, Table
|
||||
from sqlalchemy.orm import sessionmaker, mapper
|
||||
engine = create_engine( 'postgres://postgres@localhost/customers' )
|
||||
metadata = MetaData( bind=engine, reflect=True)
|
||||
Session = sessionmaker(bind=engine, autoflush=True,
|
||||
transactional=True)
|
||||
|
||||
class Customer(object): pass
|
||||
mapper( Customer, Table('customers', metadata ) )
|
||||
|
||||
session = Session()
|
||||
customer = Customer( businessName=“Jamb Safety”,
|
||||
website=“www.jamb.com” )
|
||||
session.save( customer )
|
||||
for customer in Session.query(Customer).filter(
|
||||
Customer.businessName.like(“Jamb%”)):
|
||||
print customer.businessName
|
||||
session.commit()
|
||||
|
||||
------------------------
|
||||
** release and py2exe **
|
||||
------------------------
|
||||
|
||||
from distutils.core import setup
|
||||
import py2exe
|
||||
import glob
|
||||
setup(
|
||||
name="Customers",
|
||||
author="Sankel Software",
|
||||
author_email="david@sankelsoftware.com",
|
||||
url="http://sankelsoftware.com",
|
||||
license=“GPL",
|
||||
version=“1.0.0",
|
||||
windows=[ { "script":"main.py“,}],
|
||||
options={"py2exe":{"includes":["sip”]}},
|
||||
data_files=[
|
||||
("forms",glob.glob("forms/*.ui")),
|
||||
] )
|
||||
|
||||
release:
|
||||
python setup.py py2exe --quiet --dist-dir=dist
|
@ -18,12 +18,6 @@
|
||||
.. autoclass:: openlp.core.lib.eventreceiver.EventReceiver
|
||||
:members:
|
||||
|
||||
:mod:`ListWithPreviews`
|
||||
-----------------------
|
||||
|
||||
.. autoclass:: openlp.core.lib.listwithpreviews.ListWithPreviews
|
||||
:members:
|
||||
|
||||
:mod:`MediaManagerItem`
|
||||
-----------------------
|
||||
|
||||
@ -36,12 +30,6 @@
|
||||
.. autoclass:: openlp.core.lib.plugin.Plugin
|
||||
:members:
|
||||
|
||||
:mod:`PluginConfig`
|
||||
-------------------
|
||||
|
||||
.. autoclass:: openlp.core.lib.pluginconfig.PluginConfig
|
||||
:members:
|
||||
|
||||
:mod:`PluginManager`
|
||||
--------------------
|
||||
|
||||
|
95
documentation/source/plugins/bibles.rst
Normal file
@ -0,0 +1,95 @@
|
||||
.. _plugins-bibles:
|
||||
|
||||
:mod:`bibles` Plugin
|
||||
====================
|
||||
|
||||
.. automodule:: openlp.plugins.bibles
|
||||
:members:
|
||||
|
||||
:mod:`BiblePlugin` Class
|
||||
-------------------------
|
||||
|
||||
.. autoclass:: openlp.plugins.bibles.bibleplugin.BiblePlugin
|
||||
:members:
|
||||
|
||||
:mod:`forms` Submodule
|
||||
----------------------
|
||||
|
||||
.. automodule:: openlp.plugins.bibles.forms
|
||||
:members:
|
||||
|
||||
:mod:`BibleImportWizard`
|
||||
^^^^^^^^^^^^^^^^^^^^^^^^
|
||||
|
||||
.. autoclass:: openlp.plugins.bibles.forms.bibleimportwizard.Ui_BibleImportWizard
|
||||
:members:
|
||||
|
||||
.. autoclass:: openlp.plugins.bibles.forms.importwizardform.ImportWizardForm
|
||||
:members:
|
||||
|
||||
:mod:`lib` Submodule
|
||||
--------------------
|
||||
|
||||
.. automodule:: openlp.plugins.bibles.lib
|
||||
:members:
|
||||
|
||||
:mod:`db`
|
||||
^^^^^^^^^
|
||||
|
||||
.. automodule:: openlp.plugins.bibles.lib.db
|
||||
:members:
|
||||
|
||||
.. autoclass:: openlp.plugins.bibles.lib.db.BibleDB
|
||||
:members:
|
||||
|
||||
:mod:`csv`
|
||||
^^^^^^^^^^
|
||||
|
||||
.. automodule:: openlp.plugins.bibles.lib.csvbible
|
||||
:members:
|
||||
|
||||
.. autoclass:: openlp.plugins.bibles.lib.csvbible.CSVBible
|
||||
:members:
|
||||
|
||||
:mod:`http`
|
||||
^^^^^^^^^^^
|
||||
|
||||
.. automodule:: openlp.plugins.bibles.lib.http
|
||||
:members:
|
||||
|
||||
.. autoclass:: openlp.plugins.bibles.lib.http.HTTPBible
|
||||
:members:
|
||||
|
||||
:mod:`bibleOSISimpl`
|
||||
^^^^^^^^^^^^^^^^^^^^
|
||||
|
||||
.. automodule:: openlp.plugins.bibles.lib.osis
|
||||
:members:
|
||||
|
||||
.. autoclass:: openlp.plugins.bibles.lib.osis.OSISBible
|
||||
:members:
|
||||
|
||||
:mod:`biblestab`
|
||||
^^^^^^^^^^^^^^^^
|
||||
|
||||
.. automodule:: openlp.plugins.bibles.lib.biblestab
|
||||
:members:
|
||||
|
||||
:mod:`common`
|
||||
^^^^^^^^^^^^^
|
||||
|
||||
.. automodule:: openlp.plugins.bibles.lib.common
|
||||
:members:
|
||||
|
||||
:mod:`manager`
|
||||
^^^^^^^^^^^^^^
|
||||
|
||||
.. automodule:: openlp.plugins.bibles.lib.manager
|
||||
:members:
|
||||
|
||||
:mod:`mediaitem`
|
||||
^^^^^^^^^^^^^^^^
|
||||
|
||||
.. automodule:: openlp.plugins.bibles.lib.mediaitem
|
||||
:members:
|
||||
|
@ -10,12 +10,7 @@
|
||||
:maxdepth: 2
|
||||
|
||||
songs
|
||||
|
||||
:mod:`bibles` Plugin
|
||||
--------------------
|
||||
|
||||
.. automodule:: openlp.plugins.bibles
|
||||
:members:
|
||||
bibles
|
||||
|
||||
:mod:`presentations` Plugin
|
||||
---------------------------
|
||||
@ -41,3 +36,8 @@
|
||||
.. automodule:: openlp.plugins.custom
|
||||
:members:
|
||||
|
||||
:mod:`songusage` Plugin
|
||||
-----------------------
|
||||
|
||||
.. automodule:: openlp.plugins.songusage
|
||||
:members:
|
||||
|
32
openlp.pyw
@ -34,10 +34,10 @@ from PyQt4 import QtCore, QtGui
|
||||
|
||||
log = logging.getLogger()
|
||||
|
||||
from openlp.core.lib import Receiver, str_to_bool
|
||||
from openlp.core.lib import Receiver
|
||||
from openlp.core.resources import qInitResources
|
||||
from openlp.core.ui import MainWindow, SplashScreen, ScreenList
|
||||
from openlp.core.utils import AppLocation, ConfigHelper
|
||||
from openlp.core.utils import AppLocation, LanguageManager
|
||||
|
||||
application_stylesheet = u"""
|
||||
QMainWindow::separator
|
||||
@ -78,9 +78,7 @@ class OpenLP(QtGui.QApplication):
|
||||
Run the OpenLP application.
|
||||
"""
|
||||
#Load and store current Application Version
|
||||
filepath = AppLocation.get_directory(AppLocation.AppDir)
|
||||
if not hasattr(sys, u'frozen'):
|
||||
filepath = os.path.join(filepath, u'openlp')
|
||||
filepath = AppLocation.get_directory(AppLocation.VersionDir)
|
||||
filepath = os.path.join(filepath, u'.version')
|
||||
fversion = None
|
||||
try:
|
||||
@ -112,20 +110,17 @@ class OpenLP(QtGui.QApplication):
|
||||
finally:
|
||||
if fversion:
|
||||
fversion.close()
|
||||
#set the default string encoding
|
||||
try:
|
||||
sys.setappdefaultencoding(u'utf-8')
|
||||
except:
|
||||
pass
|
||||
#provide a listener for widgets to reqest a screen update.
|
||||
QtCore.QObject.connect(Receiver.get_receiver(),
|
||||
QtCore.SIGNAL(u'process_events'), self.processEvents)
|
||||
QtCore.SIGNAL(u'openlp_process_events'), self.processEvents)
|
||||
self.setOrganizationName(u'OpenLP')
|
||||
self.setOrganizationDomain(u'openlp.org')
|
||||
self.setApplicationName(u'OpenLP')
|
||||
self.setApplicationVersion(app_version[u'version'])
|
||||
if os.name == u'nt':
|
||||
self.setStyleSheet(application_stylesheet)
|
||||
show_splash = str_to_bool(ConfigHelper.get_registry().get_value(
|
||||
u'general', u'show splash', True))
|
||||
show_splash = QtCore.QSettings().value(
|
||||
u'general/show splash', QtCore.QVariant(True)).toBool()
|
||||
if show_splash:
|
||||
self.splash = SplashScreen(self.applicationVersion())
|
||||
self.splash.show()
|
||||
@ -135,8 +130,8 @@ class OpenLP(QtGui.QApplication):
|
||||
# Decide how many screens we have and their size
|
||||
for screen in xrange(0, self.desktop().numScreens()):
|
||||
screens.add_screen({u'number': screen,
|
||||
u'size': self.desktop().availableGeometry(screen),
|
||||
u'primary': (self.desktop().primaryScreen() == screen)})
|
||||
u'size': self.desktop().availableGeometry(screen),
|
||||
u'primary': (self.desktop().primaryScreen() == screen)})
|
||||
log.info(u'Screen %d found with resolution %s',
|
||||
screen, self.desktop().availableGeometry(screen))
|
||||
# start the main app window
|
||||
@ -174,7 +169,7 @@ def main():
|
||||
filename = os.path.join(log_path, u'openlp.log')
|
||||
logfile = FileHandler(filename, u'w')
|
||||
logfile.setFormatter(logging.Formatter(
|
||||
u'%(asctime)s %(name)-20s %(levelname)-8s %(message)s'))
|
||||
u'%(asctime)s %(name)-55s %(levelname)-8s %(message)s'))
|
||||
log.addHandler(logfile)
|
||||
logging.addLevelName(15, u'Timer')
|
||||
# Parse command line options and deal with them.
|
||||
@ -195,6 +190,11 @@ def main():
|
||||
qInitResources()
|
||||
# Now create and actually run the application.
|
||||
app = OpenLP(qt_args)
|
||||
#i18n Set Language
|
||||
language = LanguageManager.get_language()
|
||||
appTranslator = LanguageManager.get_translator(language)
|
||||
app.installTranslator(appTranslator)
|
||||
|
||||
sys.exit(app.run())
|
||||
|
||||
if __name__ == u'__main__':
|
||||
|
@ -35,7 +35,7 @@ from PyQt4 import QtCore, QtGui
|
||||
|
||||
log = logging.getLogger(__name__)
|
||||
|
||||
def translate(context, text):
|
||||
def translate(context, text, comment=None):
|
||||
"""
|
||||
A special shortcut method to wrap around the Qt4 translation functions.
|
||||
This abstracts the translation procedure so that we can change it if at a
|
||||
@ -48,8 +48,8 @@ def translate(context, text):
|
||||
``text``
|
||||
The text to put into the translation tables for translation.
|
||||
"""
|
||||
return QtGui.QApplication.translate(
|
||||
context, text, None, QtGui.QApplication.UnicodeUTF8)
|
||||
return QtCore.QCoreApplication.translate(context, text,
|
||||
comment)
|
||||
|
||||
def get_text_file_string(text_file):
|
||||
"""
|
||||
@ -164,7 +164,6 @@ class ThemeLevel(object):
|
||||
|
||||
from eventreceiver import Receiver
|
||||
from settingsmanager import SettingsManager
|
||||
from pluginconfig import PluginConfig
|
||||
from plugin import PluginStatus, Plugin
|
||||
from pluginmanager import PluginManager
|
||||
from settingstab import SettingsTab
|
||||
@ -172,7 +171,7 @@ from mediamanageritem import MediaManagerItem
|
||||
from xmlrootclass import XmlRootClass
|
||||
from serviceitem import ServiceItem
|
||||
from serviceitem import ServiceItemType
|
||||
from serviceitem import ServiceItem
|
||||
from serviceitem import ItemCapabilities
|
||||
from toolbar import OpenLPToolbar
|
||||
from dockwidget import OpenLPDockWidget
|
||||
from songxmlhandler import SongXMLBuilder, SongXMLParser
|
||||
|
@ -48,5 +48,4 @@ class BaseListWithDnD(QtGui.QListWidget):
|
||||
mimeData = QtCore.QMimeData()
|
||||
drag.setMimeData(mimeData)
|
||||
mimeData.setText(self.PluginName)
|
||||
dropAction = drag.start(QtCore.Qt.CopyAction)
|
||||
|
||||
drag.start(QtCore.Qt.CopyAction)
|
||||
|
@ -43,8 +43,3 @@ class OpenLPDockWidget(QtGui.QDockWidget):
|
||||
self.setObjectName(name)
|
||||
self.setFloating(False)
|
||||
log.debug(u'Init done')
|
||||
|
||||
def closeEvent(self, event):
|
||||
self.parent.settingsmanager.setUIItemVisibility(
|
||||
self.objectName(), False)
|
||||
event.accept()
|
||||
|
@ -35,36 +35,118 @@ class EventReceiver(QtCore.QObject):
|
||||
system. This is a private class and should not be used directly
|
||||
but rather via the Receiver class.
|
||||
|
||||
``stop_import``
|
||||
Stops the Bible Import
|
||||
|
||||
``pre_load_bibles``
|
||||
Triggers the plugin to relaod the bible lists
|
||||
|
||||
``process_events``
|
||||
``openlp_process_events``
|
||||
Requests the Application to flush the events queue
|
||||
|
||||
``{plugin}_add_service_item``
|
||||
ask the plugin to push the selected items to the service item
|
||||
``openlp_version_check``
|
||||
Version has changed so pop up window.
|
||||
|
||||
``update_themes``
|
||||
``config_updated``
|
||||
Informs components the config has changed
|
||||
|
||||
``config_screen_changed``
|
||||
The display monitor has been changed
|
||||
|
||||
``slidecontroller_{live|preview}_first``
|
||||
Moves to the first slide
|
||||
|
||||
``slidecontroller_{live|preview}_next``
|
||||
Moves to the next slide
|
||||
|
||||
``slidecontroller_{live|preview}_next_noloop``
|
||||
Moves to the next slide without auto advance
|
||||
|
||||
``slidecontroller_{live|preview}_previous``
|
||||
Moves to the previous slide
|
||||
|
||||
``slidecontroller_{live|preview}_previous_noloop``
|
||||
Moves to the previous slide, without auto advance
|
||||
|
||||
``slidecontroller_{live|preview}_last``
|
||||
Moves to the last slide
|
||||
|
||||
``slidecontroller_{live|preview}_set``
|
||||
Moves to a specific slide, by index
|
||||
|
||||
``slidecontroller_{live|preview}_started``
|
||||
Broadcasts that an item has been made live/previewed
|
||||
|
||||
``slidecontroller_{live|preview}_change``
|
||||
Informs the slidecontroller that a slide change has occurred and to
|
||||
update itself
|
||||
|
||||
``slidecontroller_{live|preview}_changed``
|
||||
Broadcasts that the slidecontroller has changed the current slide
|
||||
|
||||
``slidecontroller_{live|preview}_text_request``
|
||||
Request the text for the current item in the controller
|
||||
Returns a slidecontroller_{live|preview}_text_response with an
|
||||
array of dictionaries with the tag and verse text
|
||||
|
||||
``slidecontroller_{live|preview}_blank``
|
||||
Request that the output screen is blanked
|
||||
|
||||
``slidecontroller_{live|preview}_unblank``
|
||||
Request that the output screen is unblanked
|
||||
|
||||
``slidecontroller_live_spin_delay``
|
||||
Pushes out the loop delay
|
||||
|
||||
``slidecontroller_live_stop_loop``
|
||||
Stop the loop on the main display
|
||||
|
||||
``servicemanager_previous_item``
|
||||
Display the previous item in the service
|
||||
|
||||
``servicemanager_next_item``
|
||||
Display the next item in the service
|
||||
|
||||
``servicemanager_set_item``
|
||||
Go live on a specific item, by index
|
||||
|
||||
``servicemanager_list_request``
|
||||
Request the service list. Responds with servicemanager_list_response
|
||||
containing a array of dictionaries
|
||||
|
||||
``maindisplay_blank``
|
||||
Blank the maindisplay window
|
||||
|
||||
``maindisplay_hide``
|
||||
Hide the maindisplay window
|
||||
|
||||
``maindisplay_show``
|
||||
Return the maindisplay window
|
||||
|
||||
``maindisplay_active``
|
||||
The maindisplay has been made active
|
||||
|
||||
``maindisplay_status_text``
|
||||
Changes the bottom status bar text on the maindisplay window
|
||||
|
||||
``maindisplay_blank_check``
|
||||
Check to see if the blank display message is required
|
||||
|
||||
``videodisplay_start``
|
||||
Open a media item and prepare for playing
|
||||
|
||||
``videodisplay_play``
|
||||
Start playing a media item
|
||||
|
||||
``videodisplay_pause``
|
||||
Pause a media item
|
||||
|
||||
``videodisplay_stop``
|
||||
Stop playing a media item
|
||||
|
||||
``videodisplay_background``
|
||||
Replace the background video
|
||||
|
||||
``theme_update_list``
|
||||
send out message with new themes
|
||||
|
||||
``update_global_theme``
|
||||
``theme_update_global``
|
||||
Tell the components we have a new global theme
|
||||
|
||||
``load_song_list``
|
||||
Tells the the song plugin to reload the song list
|
||||
|
||||
``load_custom_list``
|
||||
Tells the the custom plugin to reload the custom list
|
||||
|
||||
``update_spin_delay``
|
||||
Pushes out the Image loop delay
|
||||
|
||||
``request_spin_delay``
|
||||
Requests a spin delay
|
||||
|
||||
``{plugin}_start``
|
||||
Requests a plugin to start a external program
|
||||
Path and file provided in message
|
||||
@ -81,33 +163,51 @@ class EventReceiver(QtCore.QObject):
|
||||
``{plugin}_last``
|
||||
Requests a plugin to handle a last event
|
||||
|
||||
``{plugin}_slide``
|
||||
Requests a plugin to handle a go to specific slide event
|
||||
|
||||
``{plugin}_stop``
|
||||
Requests a plugin to handle a stop event
|
||||
|
||||
``{plugin}_blank``
|
||||
Requests a plugin to handle a blank screen event
|
||||
|
||||
``{plugin}_unblank``
|
||||
Requests a plugin to handle an unblank screen event
|
||||
|
||||
``{plugin}_edit``
|
||||
Requests a plugin edit a database item with the key as the payload
|
||||
|
||||
``songusage_live``
|
||||
Sends live song audit requests to the audit component
|
||||
``{plugin}_edit_clear``
|
||||
Editing has been completed
|
||||
|
||||
``audit_changed``
|
||||
Audit information may have changed
|
||||
``{plugin}_load_list``
|
||||
Tells the the plugin to reload the media manager list
|
||||
|
||||
``config_updated``
|
||||
Informs components the config has changed
|
||||
``{plugin}_preview``
|
||||
Tells the plugin it's item can be previewed
|
||||
|
||||
``preview_song``
|
||||
Tells the song plugin the edit has finished and the song can be previewed
|
||||
Only available if the edit was triggered by the Preview button.
|
||||
``{plugin}_add_service_item``
|
||||
Ask the plugin to push the selected items to the service item
|
||||
|
||||
``slidecontroller_change``
|
||||
Informs the slidecontroller that a slide change has occurred
|
||||
``alerts_text``
|
||||
Displays an alert message
|
||||
|
||||
``bibles_nobook``
|
||||
Attempt to find book resulted in no match
|
||||
|
||||
``remote_edit_clear``
|
||||
Informs all components that remote edit has been aborted.
|
||||
``bibles_showprogress``
|
||||
Show progress of bible verse import
|
||||
|
||||
``presentation types``
|
||||
Informs all components of the presentation types supported.
|
||||
``bibles_hideprogress``
|
||||
Hide progress of bible verse import
|
||||
|
||||
``bibles_stop_import``
|
||||
Stops the Bible Import
|
||||
|
||||
``remotes_poll_request``
|
||||
Waits for openlp to do something "interesting" and sends a
|
||||
remotes_poll_response signal when it does
|
||||
|
||||
"""
|
||||
def __init__(self):
|
||||
@ -164,4 +264,3 @@ class Receiver():
|
||||
Get the global ``eventreceiver`` instance.
|
||||
"""
|
||||
return Receiver.eventreceiver
|
||||
|
||||
|
@ -29,7 +29,8 @@ import os
|
||||
from PyQt4 import QtCore, QtGui
|
||||
|
||||
from openlp.core.lib.toolbar import *
|
||||
from openlp.core.lib import contextMenuAction, contextMenuSeparator
|
||||
from openlp.core.lib import contextMenuAction, contextMenuSeparator, \
|
||||
SettingsManager
|
||||
from serviceitem import ServiceItem
|
||||
|
||||
log = logging.getLogger(__name__)
|
||||
@ -69,11 +70,6 @@ class MediaManagerItem(QtGui.QWidget):
|
||||
The user visible name for a plugin which should use a suitable
|
||||
translation function.
|
||||
|
||||
``self.ConfigSection``
|
||||
The section in the configuration where the items in the media
|
||||
manager are stored. This could potentially be
|
||||
``self.PluginNameShort.lower()``.
|
||||
|
||||
``self.OnNewPrompt``
|
||||
Defaults to *'Select Image(s)'*.
|
||||
|
||||
@ -102,6 +98,7 @@ class MediaManagerItem(QtGui.QWidget):
|
||||
"""
|
||||
QtGui.QWidget.__init__(self)
|
||||
self.parent = parent
|
||||
self.settingsSection = title.lower()
|
||||
if type(icon) is QtGui.QIcon:
|
||||
self.icon = icon
|
||||
elif type(icon) is types.StringType:
|
||||
@ -114,6 +111,7 @@ class MediaManagerItem(QtGui.QWidget):
|
||||
self.Toolbar = None
|
||||
self.remoteTriggered = None
|
||||
self.ServiceItemIconName = None
|
||||
self.singleServiceItem = True
|
||||
self.addToServiceItem = False
|
||||
self.PageLayout = QtGui.QVBoxLayout(self)
|
||||
self.PageLayout.setSpacing(0)
|
||||
@ -333,24 +331,47 @@ class MediaManagerItem(QtGui.QWidget):
|
||||
def onFileClick(self):
|
||||
files = QtGui.QFileDialog.getOpenFileNames(
|
||||
self, self.OnNewPrompt,
|
||||
self.parent.config.get_last_dir(), self.OnNewFileMasks)
|
||||
SettingsManager.get_last_dir(self.settingsSection),
|
||||
self.OnNewFileMasks)
|
||||
log.info(u'New files(s) %s', unicode(files))
|
||||
if files:
|
||||
self.loadList(files)
|
||||
dir, filename = os.path.split(unicode(files[0]))
|
||||
self.parent.config.set_last_dir(dir)
|
||||
self.parent.config.set_list(self.ConfigSection, self.getFileList())
|
||||
dir = os.path.split(unicode(files[0]))[0]
|
||||
SettingsManager.set_last_dir(self.settingsSection, dir)
|
||||
SettingsManager.set_list(self.settingsSection,
|
||||
self.settingsSection, self.getFileList())
|
||||
|
||||
def getFileList(self):
|
||||
count = 0
|
||||
filelist = []
|
||||
while count < self.ListView.count():
|
||||
while count < self.ListView.count():
|
||||
bitem = self.ListView.item(count)
|
||||
filename = unicode((bitem.data(QtCore.Qt.UserRole)).toString())
|
||||
filelist.append(filename)
|
||||
count += 1
|
||||
return filelist
|
||||
|
||||
def validate(self, file, thumb):
|
||||
"""
|
||||
Validates to see if the file still exists or
|
||||
thumbnail is up to date
|
||||
"""
|
||||
if os.path.exists(file):
|
||||
filedate = os.stat(file).st_mtime
|
||||
thumbdate = os.stat(thumb).st_mtime
|
||||
#if file updated rebuild icon
|
||||
if filedate > thumbdate:
|
||||
self.IconFromFile(file, thumb)
|
||||
return True
|
||||
return False
|
||||
|
||||
def IconFromFile(self, file, thumb):
|
||||
icon = build_icon(unicode(file))
|
||||
pixmap = icon.pixmap(QtCore.QSize(88,50))
|
||||
ext = os.path.splitext(thumb)[1].lower()
|
||||
pixmap.save(thumb, ext[1:])
|
||||
return icon
|
||||
|
||||
def loadList(self, list):
|
||||
raise NotImplementedError(u'MediaManagerItem.loadList needs to be '
|
||||
u'defined by the plugin')
|
||||
@ -367,7 +388,7 @@ class MediaManagerItem(QtGui.QWidget):
|
||||
raise NotImplementedError(u'MediaManagerItem.onDeleteClick needs to '
|
||||
u'be defined by the plugin')
|
||||
|
||||
def generateSlideData(self, item):
|
||||
def generateSlideData(self, service_item, item):
|
||||
raise NotImplementedError(u'MediaManagerItem.generateSlideData needs '
|
||||
u'to be defined by the plugin')
|
||||
|
||||
@ -401,11 +422,22 @@ class MediaManagerItem(QtGui.QWidget):
|
||||
self.trUtf8('No Items Selected'),
|
||||
self.trUtf8('You must select one or more items.'))
|
||||
else:
|
||||
log.debug(self.PluginNameShort + u' Add requested')
|
||||
service_item = self.buildServiceItem()
|
||||
if service_item:
|
||||
service_item.from_plugin = False
|
||||
self.parent.service_manager.addServiceItem(service_item)
|
||||
#Is it posssible to process multiple list items to generate multiple
|
||||
#service items?
|
||||
if self.singleServiceItem or self.remoteTriggered:
|
||||
log.debug(self.PluginNameShort + u' Add requested')
|
||||
service_item = self.buildServiceItem()
|
||||
if service_item:
|
||||
service_item.from_plugin = False
|
||||
self.parent.service_manager.addServiceItem(service_item,
|
||||
replace=self.remoteTriggered)
|
||||
else:
|
||||
items = self.ListView.selectedIndexes()
|
||||
for item in items:
|
||||
service_item = self.buildServiceItem(item)
|
||||
if service_item:
|
||||
service_item.from_plugin = False
|
||||
self.parent.service_manager.addServiceItem(service_item)
|
||||
|
||||
def onAddEditClick(self):
|
||||
if not self.ListView.selectedIndexes() and not self.remoteTriggered:
|
||||
@ -418,18 +450,20 @@ class MediaManagerItem(QtGui.QWidget):
|
||||
if not service_item:
|
||||
QtGui.QMessageBox.information(self,
|
||||
self.trUtf8('No Service Item Selected'),
|
||||
self.trUtf8('You must select a existing service item to add to.'))
|
||||
elif self.title == service_item.name:
|
||||
self.trUtf8(
|
||||
'You must select an existing service item to add to.'))
|
||||
elif self.title.lower() == service_item.name.lower():
|
||||
self.generateSlideData(service_item)
|
||||
self.parent.service_manager.addServiceItem(service_item)
|
||||
self.parent.service_manager.addServiceItem(service_item,
|
||||
replace=True)
|
||||
else:
|
||||
#Turn off the remote edit update message indicator
|
||||
self.parent.service_manager.remoteEditTriggered = False
|
||||
QtGui.QMessageBox.information(self,
|
||||
self.trUtf8('Invalid Service Item'),
|
||||
self.trUtf8(unicode('You must select a %s service item.' % self.title)))
|
||||
self.trUtf8(unicode(
|
||||
'You must select a %s service item.' % self.title)))
|
||||
|
||||
def buildServiceItem(self):
|
||||
def buildServiceItem(self, item=None):
|
||||
"""
|
||||
Common method for generating a service item
|
||||
"""
|
||||
@ -439,7 +473,7 @@ class MediaManagerItem(QtGui.QWidget):
|
||||
else:
|
||||
service_item.addIcon(
|
||||
u':/media/media_' + self.PluginNameShort.lower() + u'.png')
|
||||
if self.generateSlideData(service_item):
|
||||
if self.generateSlideData(service_item, item):
|
||||
return service_item
|
||||
else:
|
||||
return None
|
||||
|
@ -24,9 +24,10 @@
|
||||
###############################################################################
|
||||
|
||||
import logging
|
||||
|
||||
from PyQt4 import QtCore
|
||||
|
||||
from openlp.core.lib import PluginConfig, Receiver
|
||||
from openlp.core.lib import Receiver
|
||||
|
||||
log = logging.getLogger(__name__)
|
||||
|
||||
@ -50,13 +51,12 @@ class Plugin(QtCore.QObject):
|
||||
``version``
|
||||
The version number of this iteration of the plugin.
|
||||
|
||||
``settingsSection``
|
||||
The namespace to store settings for the plugin.
|
||||
|
||||
``icon``
|
||||
An instance of QIcon, which holds an icon for this plugin.
|
||||
|
||||
``config``
|
||||
An instance of PluginConfig, which allows plugins to read and write to
|
||||
openlp.org's configuration. This is pre-instantiated.
|
||||
|
||||
``log``
|
||||
A log object used to log debugging messages. This is pre-instantiated.
|
||||
|
||||
@ -78,7 +78,8 @@ class Plugin(QtCore.QObject):
|
||||
Add an item to the Export menu.
|
||||
|
||||
``get_settings_tab()``
|
||||
Returns an instance of SettingsTabItem to be used in the Settings dialog.
|
||||
Returns an instance of SettingsTabItem to be used in the Settings
|
||||
dialog.
|
||||
|
||||
``add_to_menu(menubar)``
|
||||
A method to add a menu item to anywhere in the menu, given the menu bar.
|
||||
@ -115,8 +116,8 @@ class Plugin(QtCore.QObject):
|
||||
self.name = name
|
||||
if version:
|
||||
self.version = version
|
||||
self.settingsSection = self.name.lower()
|
||||
self.icon = None
|
||||
self.config = PluginConfig(self.name)
|
||||
self.weight = 0
|
||||
self.status = PluginStatus.Inactive
|
||||
# Set up logging
|
||||
@ -125,7 +126,7 @@ class Plugin(QtCore.QObject):
|
||||
self.live_controller = plugin_helpers[u'live']
|
||||
self.render_manager = plugin_helpers[u'render']
|
||||
self.service_manager = plugin_helpers[u'service']
|
||||
self.settings = plugin_helpers[u'settings']
|
||||
self.settings_form = plugin_helpers[u'settings form']
|
||||
self.mediadock = plugin_helpers[u'toolbox']
|
||||
self.maindisplay = plugin_helpers[u'maindisplay']
|
||||
QtCore.QObject.connect(Receiver.get_receiver(),
|
||||
@ -145,15 +146,17 @@ class Plugin(QtCore.QObject):
|
||||
"""
|
||||
Sets the status of the plugin
|
||||
"""
|
||||
self.status = int(self.config.get_config(u'status',
|
||||
PluginStatus.Inactive))
|
||||
self.status = QtCore.QSettings().value(
|
||||
self.settingsSection + u'/status',
|
||||
QtCore.QVariant(PluginStatus.Inactive)).toInt()[0]
|
||||
|
||||
def toggle_status(self, new_status):
|
||||
"""
|
||||
Changes the status of the plugin and remembers it
|
||||
"""
|
||||
self.status = new_status
|
||||
self.config.set_config(u'status', self.status)
|
||||
QtCore.QSettings().setValue(
|
||||
self.settingsSection + u'/status', QtCore.QVariant(self.status))
|
||||
|
||||
def is_active(self):
|
||||
"""
|
||||
@ -212,12 +215,16 @@ class Plugin(QtCore.QObject):
|
||||
"""
|
||||
pass
|
||||
|
||||
def process_add_service_event(self):
|
||||
def process_add_service_event(self, replace=False):
|
||||
"""
|
||||
Generic Drag and drop handler triggered from service_manager.
|
||||
"""
|
||||
log.debug(u'process_add_service_event event called for plugin %s' % self.name)
|
||||
self.media_item.onAddClick()
|
||||
log.debug(u'process_add_service_event event called for plugin %s' %
|
||||
self.name)
|
||||
if replace:
|
||||
self.media_item.onAddEditClick()
|
||||
else:
|
||||
self.media_item.onAddClick()
|
||||
|
||||
def about(self):
|
||||
"""
|
||||
@ -244,7 +251,7 @@ class Plugin(QtCore.QObject):
|
||||
Called by the plugin to remove toolbar
|
||||
"""
|
||||
self.mediadock.remove_dock(self.name)
|
||||
self.settings.removeTab(self.name)
|
||||
self.settings_form.removeTab(self.name)
|
||||
|
||||
def insert_toolbox_item(self):
|
||||
"""
|
||||
@ -253,7 +260,7 @@ class Plugin(QtCore.QObject):
|
||||
if self.media_item:
|
||||
self.mediadock.insert_dock(self.media_item, self.icon, self.weight)
|
||||
if self.settings_tab:
|
||||
self.settings.insertTab(self.settings_tab, self.weight)
|
||||
self.settings_form.insertTab(self.settings_tab, self.weight)
|
||||
|
||||
def can_delete_theme(self, theme):
|
||||
"""
|
||||
|
@ -1,193 +0,0 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
# vim: autoindent shiftwidth=4 expandtab textwidth=80 tabstop=4 softtabstop=4
|
||||
|
||||
###############################################################################
|
||||
# OpenLP - Open Source Lyrics Projection #
|
||||
# --------------------------------------------------------------------------- #
|
||||
# Copyright (c) 2008-2010 Raoul Snyman #
|
||||
# Portions copyright (c) 2008-2010 Tim Bentley, Jonathan Corwin, Michael #
|
||||
# Gorven, Scott Guerrieri, Christian Richter, Maikel Stuivenberg, Martin #
|
||||
# Thompson, Jon Tibble, Carsten Tinggaard #
|
||||
# --------------------------------------------------------------------------- #
|
||||
# This program is free software; you can redistribute it and/or modify it #
|
||||
# under the terms of the GNU General Public License as published by the Free #
|
||||
# Software Foundation; version 2 of the License. #
|
||||
# #
|
||||
# This program is distributed in the hope that it will be useful, but WITHOUT #
|
||||
# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or #
|
||||
# FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for #
|
||||
# more details. #
|
||||
# #
|
||||
# You should have received a copy of the GNU General Public License along #
|
||||
# with this program; if not, write to the Free Software Foundation, Inc., 59 #
|
||||
# Temple Place, Suite 330, Boston, MA 02111-1307 USA #
|
||||
###############################################################################
|
||||
|
||||
import os
|
||||
|
||||
from openlp.core.utils import ConfigHelper
|
||||
|
||||
class PluginConfig(object):
|
||||
"""
|
||||
This is a generic config helper for plugins.
|
||||
"""
|
||||
def __init__(self, plugin_name):
|
||||
"""
|
||||
Initialise the plugin config object, setting the section name to the
|
||||
plugin name.
|
||||
|
||||
``plugin_name``
|
||||
The name of the plugin to use as a section name.
|
||||
"""
|
||||
self.section = plugin_name.lower()
|
||||
|
||||
def get_config(self, key, default=None):
|
||||
"""
|
||||
Get a configuration value from the configuration registry.
|
||||
|
||||
``key``
|
||||
The name of configuration to load.
|
||||
|
||||
``default``
|
||||
Defaults to *None*. The default value to return if there is no
|
||||
other value.
|
||||
"""
|
||||
return ConfigHelper.get_config(self.section, key, default)
|
||||
|
||||
def delete_config(self, key):
|
||||
"""
|
||||
Delete a configuration value from the configuration registry.
|
||||
|
||||
``key``
|
||||
The name of the configuration to remove.
|
||||
"""
|
||||
return ConfigHelper.delete_config(self.section, key)
|
||||
|
||||
def set_config(self, key, value):
|
||||
"""
|
||||
Set a configuration value in the configuration registry.
|
||||
|
||||
``key``
|
||||
The name of the configuration to save.
|
||||
|
||||
``value``
|
||||
The value of the configuration to save.
|
||||
"""
|
||||
return ConfigHelper.set_config(self.section, key, value)
|
||||
|
||||
def get_data_path(self):
|
||||
"""
|
||||
Dynamically build the data file path for a plugin.
|
||||
"""
|
||||
#app_data = ConfigHelper.get_data_path()
|
||||
app_data = ConfigHelper.get_data_path()
|
||||
safe_name = self.section.replace(u' ',u'-')
|
||||
plugin_data = self.get_config(u'data path', safe_name)
|
||||
path = os.path.join(app_data, plugin_data)
|
||||
if not os.path.exists(path):
|
||||
os.makedirs(path)
|
||||
return path
|
||||
|
||||
def set_data_path(self, path):
|
||||
"""
|
||||
Set the data file path.
|
||||
|
||||
``path``
|
||||
The path to save.
|
||||
"""
|
||||
return self.set_config(u'data path', os.path.basename(path))
|
||||
|
||||
def get_files(self, suffix=None):
|
||||
"""
|
||||
Get a list of files from the data files path.
|
||||
|
||||
``suffix``
|
||||
Defaults to *None*. The extension to search for.
|
||||
"""
|
||||
try:
|
||||
files = os.listdir(self.get_data_path())
|
||||
except:
|
||||
return []
|
||||
if suffix:
|
||||
return_files = []
|
||||
for file in files:
|
||||
if file.find(u'.') != -1:
|
||||
filename = file.split(u'.')
|
||||
#bname = nme[0]
|
||||
filesuffix = filename[1].lower()
|
||||
filesuffix = filesuffix.lower()
|
||||
# only load files with the correct suffix
|
||||
if suffix.find(filesuffix) > -1 :
|
||||
return_files.append(file)
|
||||
return return_files
|
||||
else:
|
||||
# no filtering required
|
||||
return files
|
||||
|
||||
def load_list(self, name):
|
||||
"""
|
||||
Load a list from the config file.
|
||||
|
||||
``name``
|
||||
The name of the list.
|
||||
"""
|
||||
list_count = self.get_config(u'%s count' % name)
|
||||
if list_count:
|
||||
list_count = int(list_count)
|
||||
else:
|
||||
list_count = 0
|
||||
list = []
|
||||
if list_count > 0:
|
||||
for counter in range(0, list_count):
|
||||
item = unicode(self.get_config(u'%s %d' % (name, counter)))
|
||||
list.append(item)
|
||||
return list
|
||||
|
||||
def set_list(self, name, list):
|
||||
"""
|
||||
Save a list to the config file.
|
||||
|
||||
``name``
|
||||
The name of the list to save.
|
||||
|
||||
``list``
|
||||
The list of values to save.
|
||||
"""
|
||||
old_count = int(self.get_config(u'%s count' % name, int(0)))
|
||||
new_count = len(list)
|
||||
self.set_config(u'%s count' % name, new_count)
|
||||
for counter in range (0, new_count):
|
||||
self.set_config(u'%s %d' % (name, counter), list[counter-1])
|
||||
if old_count > new_count:
|
||||
# Tidy up any old list itrms if list is smaller now
|
||||
for counter in range(new_count, old_count):
|
||||
self.delete_config(u'%s %d' % (name, counter))
|
||||
|
||||
def get_last_dir(self, num=None):
|
||||
"""
|
||||
Read the last directory used for plugin.
|
||||
|
||||
``num``
|
||||
Defaults to *None*. A further qualifier.
|
||||
"""
|
||||
if num:
|
||||
name = u'last directory %d' % num
|
||||
else:
|
||||
name = u'last directory'
|
||||
last_dir = self.get_config(name)
|
||||
if not last_dir:
|
||||
last_dir = u''
|
||||
return last_dir
|
||||
|
||||
def set_last_dir(self, directory, num=None):
|
||||
"""
|
||||
Save the last directory used for plugin.
|
||||
|
||||
``num``
|
||||
Defaults to *None*. A further qualifier.
|
||||
"""
|
||||
if num:
|
||||
name = u'last directory %d' % num
|
||||
else:
|
||||
name = u'last directory'
|
||||
self.set_config(name, directory)
|
@ -48,8 +48,8 @@ class Renderer(object):
|
||||
self.theme_name = None
|
||||
self._theme = None
|
||||
self._bg_image_filename = None
|
||||
self._frame = None
|
||||
self._frameOp = None
|
||||
self.frame = None
|
||||
self.frame_opaque = None
|
||||
self.bg_frame = None
|
||||
self.bg_image = None
|
||||
|
||||
@ -89,10 +89,10 @@ class Renderer(object):
|
||||
"""
|
||||
log.debug(u'set bg image %s', filename)
|
||||
self._bg_image_filename = unicode(filename)
|
||||
if self._frame:
|
||||
if self.frame:
|
||||
self.bg_image = resize_image(self._bg_image_filename,
|
||||
self._frame.width(),
|
||||
self._frame.height())
|
||||
self.frame.width(),
|
||||
self.frame.height())
|
||||
|
||||
def set_frame_dest(self, frame_width, frame_height, preview=False):
|
||||
"""
|
||||
@ -111,14 +111,13 @@ class Renderer(object):
|
||||
self.bg_frame = None
|
||||
log.debug(u'set frame dest (frame) w %d h %d', frame_width,
|
||||
frame_height)
|
||||
self._frame = QtGui.QImage(frame_width, frame_height,
|
||||
self.frame = QtGui.QImage(frame_width, frame_height,
|
||||
QtGui.QImage.Format_ARGB32_Premultiplied)
|
||||
self._frameOp = QtGui.QImage(frame_width, frame_height,
|
||||
self.frame_opaque = QtGui.QImage(frame_width, frame_height,
|
||||
QtGui.QImage.Format_ARGB32_Premultiplied)
|
||||
if self._bg_image_filename and not self.bg_image:
|
||||
self.bg_image = resize_image(self._bg_image_filename,
|
||||
self._frame.width(),
|
||||
self._frame.height())
|
||||
self.frame.width(), self.frame.height())
|
||||
if self.bg_frame is None:
|
||||
self._generate_background_frame()
|
||||
|
||||
@ -223,7 +222,7 @@ class Renderer(object):
|
||||
``rect_footer``
|
||||
The footer text block.
|
||||
"""
|
||||
log.debug(u'set_text_rectangle %s , %s' %(rect_main, rect_footer) )
|
||||
log.debug(u'set_text_rectangle %s , %s' % (rect_main, rect_footer))
|
||||
self._rect = rect_main
|
||||
self._rect_footer = rect_footer
|
||||
|
||||
@ -243,8 +242,9 @@ class Renderer(object):
|
||||
if footer_lines:
|
||||
bbox1 = self._render_lines_unaligned(footer_lines, True)
|
||||
# reset the frame. first time do not worry about what you paint on.
|
||||
self._frame = QtGui.QImage(self.bg_frame)
|
||||
self._frameOp = QtGui.QImage(self.bg_frame)
|
||||
self.frame = QtGui.QImage(self.bg_frame)
|
||||
if self._theme.display_slideTransition:
|
||||
self.frame_opaque = QtGui.QImage(self.bg_frame)
|
||||
x, y = self._correctAlignment(self._rect, bbox)
|
||||
bbox = self._render_lines_unaligned(lines, False, (x, y), True)
|
||||
if footer_lines:
|
||||
@ -252,9 +252,9 @@ class Renderer(object):
|
||||
(self._rect_footer.left(), self._rect_footer.top()), True)
|
||||
log.debug(u'generate_frame_from_lines - Finish')
|
||||
if self._theme.display_slideTransition:
|
||||
return {u'main':self._frame, u'trans':self._frameOp}
|
||||
return {u'main':self.frame, u'trans':self.frame_opaque}
|
||||
else:
|
||||
return {u'main':self._frame, u'trans':None}
|
||||
return {u'main':self.frame, u'trans':None}
|
||||
|
||||
def _generate_background_frame(self):
|
||||
"""
|
||||
@ -264,36 +264,36 @@ class Renderer(object):
|
||||
assert(self._theme)
|
||||
if self._theme.background_mode == u'transparent':
|
||||
self.bg_frame = \
|
||||
QtGui.QPixmap(self._frame.width(), self._frame.height())
|
||||
QtGui.QPixmap(self.frame.width(), self.frame.height())
|
||||
self.bg_frame.fill(QtCore.Qt.transparent)
|
||||
else:
|
||||
self.bg_frame = QtGui.QImage(self._frame.width(), self._frame.height(),
|
||||
QtGui.QImage.Format_ARGB32_Premultiplied)
|
||||
self.bg_frame = QtGui.QImage(self.frame.width(),
|
||||
self.frame.height(), QtGui.QImage.Format_ARGB32_Premultiplied)
|
||||
log.debug(u'render background %s start', self._theme.background_type)
|
||||
painter = QtGui.QPainter()
|
||||
painter.begin(self.bg_frame)
|
||||
if self._theme.background_mode == u'transparent':
|
||||
painter.fillRect(self._frame.rect(), QtCore.Qt.transparent)
|
||||
painter.fillRect(self.frame.rect(), QtCore.Qt.transparent)
|
||||
else:
|
||||
if self._theme.background_type == u'solid':
|
||||
painter.fillRect(self._frame.rect(),
|
||||
painter.fillRect(self.frame.rect(),
|
||||
QtGui.QColor(self._theme.background_color))
|
||||
elif self._theme.background_type == u'gradient':
|
||||
# gradient
|
||||
gradient = None
|
||||
if self._theme.background_direction == u'horizontal':
|
||||
w = int(self._frame.width()) / 2
|
||||
w = int(self.frame.width()) / 2
|
||||
# vertical
|
||||
gradient = QtGui.QLinearGradient(w, 0, w,
|
||||
self._frame.height())
|
||||
self.frame.height())
|
||||
elif self._theme.background_direction == u'vertical':
|
||||
h = int(self._frame.height()) / 2
|
||||
h = int(self.frame.height()) / 2
|
||||
# Horizontal
|
||||
gradient = QtGui.QLinearGradient(0, h, self._frame.width(),
|
||||
gradient = QtGui.QLinearGradient(0, h, self.frame.width(),
|
||||
h)
|
||||
else:
|
||||
w = int(self._frame.width()) / 2
|
||||
h = int(self._frame.height()) / 2
|
||||
w = int(self.frame.width()) / 2
|
||||
h = int(self.frame.height()) / 2
|
||||
# Circular
|
||||
gradient = QtGui.QRadialGradient(w, h, w)
|
||||
gradient.setColorAt(0,
|
||||
@ -302,8 +302,8 @@ class Renderer(object):
|
||||
QtGui.QColor(self._theme.background_endColor))
|
||||
painter.setBrush(QtGui.QBrush(gradient))
|
||||
rectPath = QtGui.QPainterPath()
|
||||
max_x = self._frame.width()
|
||||
max_y = self._frame.height()
|
||||
max_x = self.frame.width()
|
||||
max_y = self.frame.height()
|
||||
rectPath.moveTo(0, 0)
|
||||
rectPath.lineTo(0, max_y)
|
||||
rectPath.lineTo(max_x, max_y)
|
||||
@ -312,7 +312,7 @@ class Renderer(object):
|
||||
painter.drawPath(rectPath)
|
||||
elif self._theme.background_type == u'image':
|
||||
# image
|
||||
painter.fillRect(self._frame.rect(), QtCore.Qt.black)
|
||||
painter.fillRect(self.frame.rect(), QtCore.Qt.black)
|
||||
if self.bg_image:
|
||||
painter.drawImage(0, 0, self.bg_image)
|
||||
painter.end()
|
||||
@ -378,7 +378,7 @@ class Renderer(object):
|
||||
retval = QtCore.QRect(x, y, brx - x, bry - y)
|
||||
if self._debug:
|
||||
painter = QtGui.QPainter()
|
||||
painter.begin(self._frame)
|
||||
painter.begin(self.frame)
|
||||
painter.setPen(QtGui.QPen(QtGui.QColor(0, 0, 255)))
|
||||
painter.drawRect(retval)
|
||||
painter.end()
|
||||
@ -414,11 +414,11 @@ class Renderer(object):
|
||||
starty = y
|
||||
rightextent = None
|
||||
self.painter = QtGui.QPainter()
|
||||
self.painter.begin(self._frame)
|
||||
self.painter.begin(self.frame)
|
||||
self.painter.setRenderHint(QtGui.QPainter.Antialiasing)
|
||||
if self._theme.display_slideTransition:
|
||||
self.painter2 = QtGui.QPainter()
|
||||
self.painter2.begin(self._frameOp)
|
||||
self.painter2.begin(self.frame_opaque)
|
||||
self.painter2.setRenderHint(QtGui.QPainter.Antialiasing)
|
||||
self.painter2.setOpacity(0.7)
|
||||
# dont allow alignment messing with footers
|
||||
@ -463,10 +463,11 @@ class Renderer(object):
|
||||
# now draw the text, and any outlines/shadows
|
||||
if self._theme.display_shadow:
|
||||
self._get_extent_and_render(line, footer,
|
||||
tlcorner=(x + display_shadow_size, y + display_shadow_size),
|
||||
draw=True, color = self._theme.display_shadow_color)
|
||||
self._get_extent_and_render(line, footer, tlcorner=(x, y), draw=True,
|
||||
outline_size=display_outline_size)
|
||||
tlcorner=(x + display_shadow_size,
|
||||
y + display_shadow_size),
|
||||
draw=True, color = self._theme.display_shadow_color)
|
||||
self._get_extent_and_render(line, footer, tlcorner=(x, y),
|
||||
draw=True, outline_size=display_outline_size)
|
||||
y += h
|
||||
if linenum == 0:
|
||||
self._first_line_right_extent = rightextent
|
||||
@ -532,7 +533,10 @@ class Renderer(object):
|
||||
font = self.mainFont
|
||||
metrics = QtGui.QFontMetrics(font)
|
||||
w = metrics.width(line)
|
||||
h = metrics.height()
|
||||
if footer:
|
||||
h = metrics.height()
|
||||
else:
|
||||
h = metrics.height() + int(self._theme.font_main_line_adjustment)
|
||||
if draw:
|
||||
self.painter.setFont(font)
|
||||
if color is None:
|
||||
@ -543,27 +547,29 @@ class Renderer(object):
|
||||
else:
|
||||
pen = QtGui.QColor(color)
|
||||
x, y = tlcorner
|
||||
rowpos = y + metrics.ascent()
|
||||
if self._theme.display_outline and outline_size != 0 and not footer:
|
||||
path = QtGui.QPainterPath()
|
||||
path.addText(QtCore.QPointF(x, y + metrics.ascent()), font, line)
|
||||
path.addText(QtCore.QPointF(x, rowpos), font, line)
|
||||
self.painter.setBrush(self.painter.pen().brush())
|
||||
self.painter.setPen(QtGui.QPen(
|
||||
QtGui.QColor(self._theme.display_outline_color), outline_size))
|
||||
self.painter.setPen(QtGui.QPen(QtGui.QColor(
|
||||
self._theme.display_outline_color), outline_size))
|
||||
self.painter.drawPath(path)
|
||||
self.painter.setPen(pen)
|
||||
self.painter.drawText(x, y + metrics.ascent(), line)
|
||||
self.painter.drawText(x, rowpos, line)
|
||||
if self._theme.display_slideTransition:
|
||||
# Print 2nd image with 70% weight
|
||||
if self._theme.display_outline and outline_size != 0 and not footer:
|
||||
path = QtGui.QPainterPath()
|
||||
path.addText(QtCore.QPointF(x, y + metrics.ascent()), font, line)
|
||||
path.addText(QtCore.QPointF(x, rowpos), font, line)
|
||||
self.painter2.setBrush(self.painter2.pen().brush())
|
||||
self.painter2.setPen(QtGui.QPen(
|
||||
QtGui.QColor(self._theme.display_outline_color), outline_size))
|
||||
QtGui.QColor(self._theme.display_outline_color),
|
||||
outline_size))
|
||||
self.painter2.drawPath(path)
|
||||
self.painter2.setFont(font)
|
||||
self.painter2.setPen(pen)
|
||||
self.painter2.drawText(x, y + metrics.ascent(), line)
|
||||
self.painter2.drawText(x, rowpos, line)
|
||||
return (w, h)
|
||||
|
||||
def snoop_Image(self, image, image2=None):
|
||||
|
@ -49,7 +49,7 @@ class RenderManager(object):
|
||||
"""
|
||||
log.info(u'RenderManager Loaded')
|
||||
|
||||
def __init__(self, theme_manager, screens, screen_number=0):
|
||||
def __init__(self, theme_manager, screens):
|
||||
"""
|
||||
Initialise the render manager.
|
||||
"""
|
||||
@ -57,7 +57,6 @@ class RenderManager(object):
|
||||
self.screens = screens
|
||||
self.theme_manager = theme_manager
|
||||
self.renderer = Renderer()
|
||||
self.screens.set_current_display(screen_number)
|
||||
self.calculate_default(self.screens.current[u'size'])
|
||||
self.theme = u''
|
||||
self.service_theme = u''
|
||||
@ -65,12 +64,9 @@ class RenderManager(object):
|
||||
self.override_background = None
|
||||
self.themedata = None
|
||||
|
||||
def update_display(self, screen_number):
|
||||
def update_display(self):
|
||||
"""
|
||||
Updates the render manager's information about the current screen.
|
||||
|
||||
``screen_number``
|
||||
The updated index of the output/display screen.
|
||||
"""
|
||||
log.debug(u'Update Display')
|
||||
self.calculate_default(self.screens.current[u'size'])
|
||||
|
@ -30,7 +30,7 @@ import uuid
|
||||
|
||||
from PyQt4 import QtGui
|
||||
|
||||
from openlp.core.lib import build_icon, Receiver, resize_image
|
||||
from openlp.core.lib import build_icon, resize_image
|
||||
|
||||
log = logging.getLogger(__name__)
|
||||
|
||||
@ -42,6 +42,14 @@ class ServiceItemType(object):
|
||||
Image = 2
|
||||
Command = 3
|
||||
|
||||
class ItemCapabilities(object):
|
||||
AllowsPreview = 1
|
||||
AllowsEdit = 2
|
||||
AllowsMaintain = 3
|
||||
RequiresMedia = 4
|
||||
AllowsLoop = 5
|
||||
AllowsAdditions = 6
|
||||
|
||||
class ServiceItem(object):
|
||||
"""
|
||||
The service item is a base class for the plugins to use to interact with
|
||||
@ -67,14 +75,20 @@ class ServiceItem(object):
|
||||
self.raw_footer = None
|
||||
self.theme = None
|
||||
self.service_item_type = None
|
||||
self.edit_enabled = False
|
||||
self.maintain_allowed = False
|
||||
self._raw_frames = []
|
||||
self._display_frames = []
|
||||
self._uuid = unicode(uuid.uuid1())
|
||||
self.auto_preview_allowed = False
|
||||
self.notes = u''
|
||||
self.from_plugin = False
|
||||
self.capabilities = []
|
||||
self.is_valid = True
|
||||
self.cache = []
|
||||
|
||||
def add_capability(self, capability):
|
||||
self.capabilities.append(capability)
|
||||
|
||||
def is_capable(self, capability):
|
||||
return capability in self.capabilities
|
||||
|
||||
def addIcon(self, icon):
|
||||
"""
|
||||
@ -94,6 +108,7 @@ class ServiceItem(object):
|
||||
"""
|
||||
log.debug(u'Render called')
|
||||
self._display_frames = []
|
||||
self.cache = []
|
||||
if self.service_item_type == ServiceItemType.Text:
|
||||
log.debug(u'Formatting slides')
|
||||
if self.theme is None:
|
||||
@ -112,6 +127,7 @@ class ServiceItem(object):
|
||||
lines += line + u'\n'
|
||||
self._display_frames.append({u'title': title, \
|
||||
u'text': lines.rstrip(), u'verseTag': slide[u'verseTag'] })
|
||||
self.cache.insert(len(self._display_frames), None)
|
||||
log.log(15, u'Formatting took %4s' % (time.time() - before))
|
||||
elif self.service_item_type == ServiceItemType.Image:
|
||||
for slide in self._raw_frames:
|
||||
@ -136,11 +152,15 @@ class ServiceItem(object):
|
||||
self.RenderManager.set_override_theme(self.theme)
|
||||
format = self._display_frames[row][u'text'].split(u'\n')
|
||||
#if screen blank then do not display footer
|
||||
if format[0]:
|
||||
frame = self.RenderManager.generate_slide(format,
|
||||
self.raw_footer)
|
||||
if self.cache[row] is not None:
|
||||
frame = self.cache[row]
|
||||
else:
|
||||
frame = self.RenderManager.generate_slide(format,u'')
|
||||
if format[0]:
|
||||
frame = self.RenderManager.generate_slide(format,
|
||||
self.raw_footer)
|
||||
else:
|
||||
frame = self.RenderManager.generate_slide(format,u'')
|
||||
self.cache[row] = frame
|
||||
return frame
|
||||
|
||||
def add_from_image(self, path, title, image):
|
||||
@ -207,10 +227,8 @@ class ServiceItem(object):
|
||||
u'type':self.service_item_type,
|
||||
u'audit':self.audit,
|
||||
u'notes':self.notes,
|
||||
u'preview':self.auto_preview_allowed,
|
||||
u'edit':self.edit_enabled,
|
||||
u'maintain':self.maintain_allowed,
|
||||
u'from_plugin':self.from_plugin
|
||||
u'from_plugin':self.from_plugin,
|
||||
u'capabilities':self.capabilities
|
||||
}
|
||||
service_data = []
|
||||
if self.service_item_type == ServiceItemType.Text:
|
||||
@ -244,11 +262,9 @@ class ServiceItem(object):
|
||||
self.addIcon(header[u'icon'])
|
||||
self.raw_footer = header[u'footer']
|
||||
self.audit = header[u'audit']
|
||||
self.auto_preview_allowed = header[u'preview']
|
||||
self.notes = header[u'notes']
|
||||
self.edit_enabled = header[u'edit']
|
||||
self.maintain_allowed = header[u'maintain']
|
||||
self.from_plugin = header[u'from_plugin']
|
||||
self.capabilities = header[u'capabilities']
|
||||
if self.service_item_type == ServiceItemType.Text:
|
||||
for slide in serviceitem[u'serviceitem'][u'data']:
|
||||
self._raw_frames.append(slide)
|
||||
@ -284,11 +300,8 @@ class ServiceItem(object):
|
||||
"""
|
||||
return self._uuid != other._uuid
|
||||
|
||||
def is_song(self):
|
||||
return self.name.lower() == u'songs'
|
||||
|
||||
def is_media(self):
|
||||
return self.name.lower() == u'media'
|
||||
return ItemCapabilities.RequiresMedia in self.capabilities
|
||||
|
||||
def is_command(self):
|
||||
return self.service_item_type == ServiceItemType.Command
|
||||
@ -330,7 +343,3 @@ class ServiceItem(object):
|
||||
Returns the title of the raw frame
|
||||
"""
|
||||
return self._raw_frames[row][u'path']
|
||||
|
||||
def request_audit(self):
|
||||
if self.audit:
|
||||
Receiver.send_message(u'songusage_live', self.audit)
|
||||
|
@ -23,14 +23,16 @@
|
||||
# Temple Place, Suite 330, Boston, MA 02111-1307 USA #
|
||||
###############################################################################
|
||||
|
||||
from openlp.core.lib import str_to_bool
|
||||
from openlp.core.utils import ConfigHelper
|
||||
import os
|
||||
|
||||
from PyQt4 import QtCore
|
||||
|
||||
from openlp.core.utils import AppLocation
|
||||
|
||||
class SettingsManager(object):
|
||||
"""
|
||||
Class to control the size of the UI components so they size correctly.
|
||||
This class is created by the main window and then calculates the size of
|
||||
individual components.
|
||||
Class to control the initial settings for the UI and provide helper
|
||||
functions for the loading and saving of application settings.
|
||||
"""
|
||||
def __init__(self, screen):
|
||||
self.screen = screen.current
|
||||
@ -50,26 +52,131 @@ class SettingsManager(object):
|
||||
self.mainwindow_left + self.mainwindow_right) - 100 ) / 2
|
||||
self.slidecontroller_image = self.slidecontroller - 50
|
||||
|
||||
self.showMediaManager = str_to_bool(ConfigHelper.get_config(
|
||||
u'user interface', u'media manager', True))
|
||||
self.showServiceManager = str_to_bool(ConfigHelper.get_config(
|
||||
u'user interface', u'service manager', True))
|
||||
self.showThemeManager = str_to_bool(ConfigHelper.get_config(
|
||||
u'user interface', u'theme manager', True))
|
||||
self.showPreviewPanel = str_to_bool(ConfigHelper.get_config(
|
||||
u'user interface', u'preview panel', True))
|
||||
|
||||
def setUIItemVisibility(self, item=u'', isVisible=True):
|
||||
if item:
|
||||
if item == u'ThemeManagerDock':
|
||||
ConfigHelper.set_config(u'user interface',
|
||||
u'theme manager', isVisible)
|
||||
elif item == u'ServiceManagerDock':
|
||||
ConfigHelper.set_config(u'user interface',
|
||||
u'service manager', isVisible)
|
||||
elif item == u'MediaManagerDock':
|
||||
ConfigHelper.set_config(u'user interface',
|
||||
u'media manager', isVisible)
|
||||
self.showPreviewPanel = QtCore.QSettings().value(
|
||||
u'user interface/preview panel', QtCore.QVariant(True)).toBool()
|
||||
|
||||
def togglePreviewPanel(self, isVisible):
|
||||
ConfigHelper.set_config(u'user interface', u'preview panel', isVisible)
|
||||
QtCore.QSettings().setValue(u'user interface/preview panel',
|
||||
QtCore.QVariant(isVisible))
|
||||
|
||||
@staticmethod
|
||||
def get_last_dir(section, num=None):
|
||||
"""
|
||||
Read the last directory used for plugin.
|
||||
|
||||
``section``
|
||||
The section of code calling the method. This is used in the
|
||||
settings key.
|
||||
|
||||
``num``
|
||||
Defaults to *None*. A further qualifier.
|
||||
"""
|
||||
if num:
|
||||
name = u'last directory %d' % num
|
||||
else:
|
||||
name = u'last directory'
|
||||
last_dir = unicode(QtCore.QSettings().value(
|
||||
section + u'/' + name, QtCore.QVariant(u'')).toString())
|
||||
return last_dir
|
||||
|
||||
@staticmethod
|
||||
def set_last_dir(section, directory, num=None):
|
||||
"""
|
||||
Save the last directory used for plugin.
|
||||
|
||||
``section``
|
||||
The section of code calling the method. This is used in the
|
||||
settings key.
|
||||
|
||||
``directory``
|
||||
The directory being stored in the settings.
|
||||
|
||||
``num``
|
||||
Defaults to *None*. A further qualifier.
|
||||
"""
|
||||
if num:
|
||||
name = u'last directory %d' % num
|
||||
else:
|
||||
name = u'last directory'
|
||||
QtCore.QSettings().setValue(
|
||||
section + u'/' + name, QtCore.QVariant(directory))
|
||||
|
||||
@staticmethod
|
||||
def set_list(section, name, list):
|
||||
"""
|
||||
Save a list to application settings.
|
||||
|
||||
``section``
|
||||
The section of the settings to store this list.
|
||||
|
||||
``name``
|
||||
The name of the list to save.
|
||||
|
||||
``list``
|
||||
The list of values to save.
|
||||
"""
|
||||
settings = QtCore.QSettings()
|
||||
settings.beginGroup(section)
|
||||
old_count = settings.value(
|
||||
u'%s count' % name, QtCore.QVariant(0)).toInt()[0]
|
||||
new_count = len(list)
|
||||
settings.setValue(u'%s count' % name, QtCore.QVariant(new_count))
|
||||
for counter in range (0, new_count):
|
||||
settings.setValue(
|
||||
u'%s %d' % (name, counter), QtCore.QVariant(list[counter-1]))
|
||||
if old_count > new_count:
|
||||
# Tidy up any old list items
|
||||
for counter in range(new_count, old_count):
|
||||
settings.remove(u'%s %d' % (name, counter))
|
||||
settings.endGroup()
|
||||
|
||||
@staticmethod
|
||||
def load_list(section, name):
|
||||
"""
|
||||
Load a list from the config file.
|
||||
|
||||
``section``
|
||||
The section of the settings to load the list from.
|
||||
|
||||
``name``
|
||||
The name of the list.
|
||||
"""
|
||||
settings = QtCore.QSettings()
|
||||
settings.beginGroup(section)
|
||||
list_count = settings.value(
|
||||
u'%s count' % name, QtCore.QVariant(0)).toInt()[0]
|
||||
list = []
|
||||
if list_count:
|
||||
for counter in range(0, list_count):
|
||||
item = unicode(
|
||||
settings.value(u'%s %d' % (name, counter)).toString())
|
||||
if item:
|
||||
list.append(item)
|
||||
settings.endGroup()
|
||||
return list
|
||||
|
||||
@staticmethod
|
||||
def get_files(section=None, extension=None):
|
||||
"""
|
||||
Get a list of files from the data files path.
|
||||
|
||||
``section``
|
||||
Defaults to *None*. The section of code getting the files - used
|
||||
to load from a section's data subdirectory.
|
||||
|
||||
``extension``
|
||||
Defaults to *None*. The extension to search for.
|
||||
"""
|
||||
path = AppLocation.get_data_path()
|
||||
if section:
|
||||
path = os.path.join(path, section)
|
||||
try:
|
||||
files = os.listdir(path)
|
||||
except:
|
||||
return []
|
||||
if extension:
|
||||
return [file for file in files
|
||||
if extension == os.path.splitext(file)[1]]
|
||||
else:
|
||||
# no filtering required
|
||||
return files
|
||||
|
@ -25,35 +25,26 @@
|
||||
|
||||
from PyQt4 import QtGui
|
||||
|
||||
from openlp.core.lib import PluginConfig
|
||||
|
||||
class SettingsTab(QtGui.QWidget):
|
||||
"""
|
||||
SettingsTab is a helper widget for plugins to define Tabs for the settings
|
||||
dialog.
|
||||
"""
|
||||
def __init__(self, title, section=None):
|
||||
def __init__(self, title):
|
||||
"""
|
||||
Constructor to create the Settings tab item.
|
||||
|
||||
``title``
|
||||
Defaults to *None*. The title of the tab, which is usually
|
||||
displayed on the tab.
|
||||
|
||||
``section``
|
||||
Defaults to *None*. This is the section in the configuration file
|
||||
to write to when the ``save`` method is called.
|
||||
The title of the tab, which is usually displayed on the tab.
|
||||
"""
|
||||
QtGui.QWidget.__init__(self)
|
||||
self.tabTitle = title
|
||||
self.tabTitleVisible = None
|
||||
self.settingsSection = self.tabTitle.lower()
|
||||
self.setupUi()
|
||||
self.retranslateUi()
|
||||
self.initialise()
|
||||
if section is None:
|
||||
self.config = PluginConfig(title)
|
||||
else:
|
||||
self.config = PluginConfig(section)
|
||||
self.preLoad()
|
||||
self.load()
|
||||
|
||||
def setupUi(self):
|
||||
@ -62,6 +53,12 @@ class SettingsTab(QtGui.QWidget):
|
||||
"""
|
||||
pass
|
||||
|
||||
def preLoad(self):
|
||||
"""
|
||||
Setup the tab's interface.
|
||||
"""
|
||||
pass
|
||||
|
||||
def retranslateUi(self):
|
||||
"""
|
||||
Setup the interface translation strings.
|
||||
|
@ -53,6 +53,7 @@ blankthemexml=\
|
||||
<weight>Normal</weight>
|
||||
<italics>False</italics>
|
||||
<indentation>0</indentation>
|
||||
<line_adjustment>0</line_adjustment>
|
||||
<location override="False" x="10" y="10" width="1004" height="730"/>
|
||||
</font>
|
||||
<font type="footer">
|
||||
@ -62,6 +63,7 @@ blankthemexml=\
|
||||
<weight>Normal</weight>
|
||||
<italics>False</italics>
|
||||
<indentation>0</indentation>
|
||||
<line_adjustment>0</line_adjustment>
|
||||
<location override="False" x="10" y="730" width="1004" height="38"/>
|
||||
</font>
|
||||
<display>
|
||||
@ -171,8 +173,8 @@ class ThemeXML(object):
|
||||
self.child_element(background, u'filename', filename)
|
||||
|
||||
def add_font(self, name, color, proportion, override, fonttype=u'main',
|
||||
weight=u'Normal', italics=u'False', indentation=0, xpos=0, ypos=0,
|
||||
width=0, height=0):
|
||||
weight=u'Normal', italics=u'False', indentation=0, line_adjustment=0,
|
||||
xpos=0, ypos=0, width=0, height=0):
|
||||
"""
|
||||
Add a Font.
|
||||
|
||||
@ -227,6 +229,8 @@ class ThemeXML(object):
|
||||
self.child_element(background, u'italics', italics)
|
||||
#Create indentation name element
|
||||
self.child_element(background, u'indentation', unicode(indentation))
|
||||
#Create indentation name element
|
||||
self.child_element(background, u'line_adjustment', unicode(line_adjustment))
|
||||
|
||||
#Create Location element
|
||||
element = self.theme_xml.createElement(u'location')
|
||||
|
@ -117,10 +117,11 @@ class OpenLPToolbar(QtGui.QToolBar):
|
||||
The title of the icon to search for.
|
||||
"""
|
||||
title = QtCore.QString(title)
|
||||
if self.icons[title]:
|
||||
return self.icons[title]
|
||||
else:
|
||||
log.error(u'getIconFromTitle - no icon for %s' % title)
|
||||
try:
|
||||
if self.icons[title]:
|
||||
return self.icons[title]
|
||||
except:
|
||||
log.exception(u'getIconFromTitle - no icon for %s' % title)
|
||||
return QtGui.QIcon()
|
||||
|
||||
def makeWidgetsInvisible(self, widgets):
|
||||
|
@ -1,19 +0,0 @@
|
||||
<?xml version="1.0" encoding="iso-8859-1"?>
|
||||
<Theme>
|
||||
<Name>openlp.org Packaged Theme</Name>
|
||||
<BackgroundType>0</BackgroundType>
|
||||
<BackgroundParameter1>clWhite</BackgroundParameter1>
|
||||
<BackgroundParameter2/>
|
||||
<BackgroundParameter3/>
|
||||
<FontName>Tahoma</FontName>
|
||||
<FontColor>$00007F</FontColor>
|
||||
<FontProportion>53</FontProportion>
|
||||
<FontUnits>pixels</FontUnits>
|
||||
<Shadow>0</Shadow>
|
||||
<ShadowColor>$000000</ShadowColor>
|
||||
<Outline>0</Outline>
|
||||
<OutlineColor>$000000</OutlineColor>
|
||||
<HorizontalAlign>0</HorizontalAlign>
|
||||
<VerticalAlign>0</VerticalAlign>
|
||||
<WrapStyle>1</WrapStyle>
|
||||
</Theme>
|
Before Width: | Height: | Size: 197 KiB |
Before Width: | Height: | Size: 26 KiB |
Before Width: | Height: | Size: 194 KiB |
Before Width: | Height: | Size: 517 KiB |
Before Width: | Height: | Size: 67 KiB |
Before Width: | Height: | Size: 1.4 MiB |
Before Width: | Height: | Size: 1.4 MiB |
Before Width: | Height: | Size: 1.4 MiB |
Before Width: | Height: | Size: 1.4 MiB |
Before Width: | Height: | Size: 1.4 MiB |
Before Width: | Height: | Size: 1.4 MiB |
Before Width: | Height: | Size: 1.4 MiB |
Before Width: | Height: | Size: 1.4 MiB |
Before Width: | Height: | Size: 1.4 MiB |
Before Width: | Height: | Size: 1.4 MiB |
Before Width: | Height: | Size: 1.4 MiB |
Before Width: | Height: | Size: 1.4 MiB |
Before Width: | Height: | Size: 1.4 MiB |
Before Width: | Height: | Size: 1.4 MiB |
Before Width: | Height: | Size: 1.4 MiB |
Before Width: | Height: | Size: 1.4 MiB |
@ -1,110 +0,0 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
# vim: autoindent shiftwidth=4 expandtab textwidth=80 tabstop=4 softtabstop=4
|
||||
|
||||
###############################################################################
|
||||
# OpenLP - Open Source Lyrics Projection #
|
||||
# --------------------------------------------------------------------------- #
|
||||
# Copyright (c) 2008-2010 Raoul Snyman #
|
||||
# Portions copyright (c) 2008-2010 Tim Bentley, Jonathan Corwin, Michael #
|
||||
# Gorven, Scott Guerrieri, Christian Richter, Maikel Stuivenberg, Martin #
|
||||
# Thompson, Jon Tibble, Carsten Tinggaard #
|
||||
# --------------------------------------------------------------------------- #
|
||||
# This program is free software; you can redistribute it and/or modify it #
|
||||
# under the terms of the GNU General Public License as published by the Free #
|
||||
# Software Foundation; version 2 of the License. #
|
||||
# #
|
||||
# This program is distributed in the hope that it will be useful, but WITHOUT #
|
||||
# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or #
|
||||
# FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for #
|
||||
# more details. #
|
||||
# #
|
||||
# You should have received a copy of the GNU General Public License along #
|
||||
# with this program; if not, write to the Free Software Foundation, Inc., 59 #
|
||||
# Temple Place, Suite 330, Boston, MA 02111-1307 USA #
|
||||
###############################################################################
|
||||
|
||||
import logging
|
||||
import os
|
||||
import sys
|
||||
|
||||
from PyQt4 import QtCore, QtGui
|
||||
|
||||
from openlp.core.lib import MediaManagerItem
|
||||
|
||||
logging.basicConfig(level=logging.DEBUG,
|
||||
format='%(asctime)s %(name)-30s %(levelname)-8s %(message)s',
|
||||
datefmt='%m-%d %H:%M',
|
||||
filename='plugins.log',
|
||||
filemode='w')
|
||||
|
||||
console=logging.StreamHandler()
|
||||
# set a format which is simpler for console use
|
||||
formatter = logging.Formatter(u'%(name)24s: %(levelname)-8s %(message)s')
|
||||
# tell the handler to use this format
|
||||
console.setFormatter(formatter)
|
||||
logging.getLogger(u'').addHandler(console)
|
||||
log = logging.getLogger(u'')
|
||||
logging.info(u'Logging started')
|
||||
mypath = os.path.split(os.path.abspath(__file__))[0]
|
||||
sys.path.insert(0,(os.path.join(mypath, '..' ,'..', '..')))
|
||||
|
||||
class TestMediaManager:
|
||||
def setup_class(self):
|
||||
self.app = QtGui.QApplication([])
|
||||
logging.info (u'App is ' + unicode(self.app))
|
||||
self.main_window = QtGui.QMainWindow()
|
||||
self.main_window.resize(200, 600)
|
||||
self.MediaManagerDock = QtGui.QDockWidget(self.main_window)
|
||||
sizePolicy = QtGui.QSizePolicy(QtGui.QSizePolicy.Expanding,
|
||||
QtGui.QSizePolicy.Expanding)
|
||||
sizePolicy.setHorizontalStretch(0)
|
||||
sizePolicy.setVerticalStretch(0)
|
||||
sizePolicy.setHeightForWidth(
|
||||
self.MediaManagerDock.sizePolicy().hasHeightForWidth())
|
||||
self.MediaManagerDock.setSizePolicy(sizePolicy)
|
||||
icon = QtGui.QIcon()
|
||||
icon.addPixmap(QtGui.QPixmap(u':/system/system_mediamanager.png'),
|
||||
QtGui.QIcon.Normal, QtGui.QIcon.Off)
|
||||
self.MediaManagerDock.setWindowIcon(icon)
|
||||
self.MediaManagerDock.setFloating(False)
|
||||
self.MediaManagerContents = QtGui.QWidget()
|
||||
sizePolicy = QtGui.QSizePolicy(QtGui.QSizePolicy.Expanding,
|
||||
QtGui.QSizePolicy.Expanding)
|
||||
sizePolicy.setHorizontalStretch(0)
|
||||
sizePolicy.setVerticalStretch(0)
|
||||
sizePolicy.setHeightForWidth(
|
||||
self.MediaManagerContents.sizePolicy().hasHeightForWidth())
|
||||
self.MediaManagerContents.setSizePolicy(sizePolicy)
|
||||
self.MediaManagerLayout = QtGui.QHBoxLayout(self.MediaManagerContents)
|
||||
self.MediaManagerLayout.setContentsMargins(0, 2, 0, 0)
|
||||
self.MediaToolBox = QtGui.QToolBox(self.MediaManagerContents)
|
||||
self.MediaManagerDock.setWidget(self.MediaManagerContents)
|
||||
self.main_window.addDockWidget(QtCore.Qt.DockWidgetArea(1),
|
||||
self.MediaManagerDock)
|
||||
self.MediaManagerLayout.addWidget(self.MediaToolBox)
|
||||
def test1(self):
|
||||
log=logging.getLogger(u'test1')
|
||||
log.info(u'Start')
|
||||
i1=MediaManagerItem(self.MediaToolBox)
|
||||
i2=MediaManagerItem(self.MediaToolBox)
|
||||
log.info(u'i1'+unicode(i1))
|
||||
log.info(u'i2'+unicode(i2))
|
||||
i1.addToolbar()
|
||||
i1.addToolbarButton(u'Test1', u'Test1', None)
|
||||
i2.addToolbar()
|
||||
i2.addToolbarButton(u'Test2', u'Test2', None)
|
||||
self.MediaToolBox.setItemText(
|
||||
self.MediaToolBox.indexOf(i1), self.trUtf8('Item1'))
|
||||
self.MediaToolBox.setItemText(
|
||||
self.MediaToolBox.indexOf(i2), self.trUtf8('Item2'))
|
||||
log.info(u'Show window')
|
||||
self.main_window.show()
|
||||
log.info(u'End')
|
||||
return 1
|
||||
|
||||
if __name__ == "__main__":
|
||||
t=TestMediaManager()
|
||||
t.setup_class()
|
||||
t.test1()
|
||||
log.info(u'exec')
|
||||
sys.exit(t.app.exec_())
|
@ -1,74 +0,0 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
# vim: autoindent shiftwidth=4 expandtab textwidth=80 tabstop=4 softtabstop=4
|
||||
|
||||
###############################################################################
|
||||
# OpenLP - Open Source Lyrics Projection #
|
||||
# --------------------------------------------------------------------------- #
|
||||
# Copyright (c) 2008-2010 Raoul Snyman #
|
||||
# Portions copyright (c) 2008-2010 Tim Bentley, Jonathan Corwin, Michael #
|
||||
# Gorven, Scott Guerrieri, Christian Richter, Maikel Stuivenberg, Martin #
|
||||
# Thompson, Jon Tibble, Carsten Tinggaard #
|
||||
# --------------------------------------------------------------------------- #
|
||||
# This program is free software; you can redistribute it and/or modify it #
|
||||
# under the terms of the GNU General Public License as published by the Free #
|
||||
# Software Foundation; version 2 of the License. #
|
||||
# #
|
||||
# This program is distributed in the hope that it will be useful, but WITHOUT #
|
||||
# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or #
|
||||
# FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for #
|
||||
# more details. #
|
||||
# #
|
||||
# You should have received a copy of the GNU General Public License along #
|
||||
# with this program; if not, write to the Free Software Foundation, Inc., 59 #
|
||||
# Temple Place, Suite 330, Boston, MA 02111-1307 USA #
|
||||
###############################################################################
|
||||
|
||||
import logging
|
||||
import os
|
||||
import sys
|
||||
|
||||
from openlp.core.lib.pluginmanager import PluginManager
|
||||
|
||||
logging.basicConfig(level=logging.DEBUG,
|
||||
format='%(asctime)s %(name)-12s %(levelname)-8s %(message)s',
|
||||
datefmt='%m-%d %H:%M',
|
||||
filename='plugins.log',
|
||||
filemode='w')
|
||||
|
||||
console=logging.StreamHandler()
|
||||
# set a format which is simpler for console use
|
||||
formatter = logging.Formatter(u'%(name)-12s: %(levelname)-8s %(message)s')
|
||||
# tell the handler to use this format
|
||||
console.setFormatter(formatter)
|
||||
logging.getLogger(u'').addHandler(console)
|
||||
log = logging.getLogger(u'')
|
||||
logging.info(u'Logging started')
|
||||
mypath = os.path.split(os.path.abspath(__file__))[0]
|
||||
sys.path.insert(0,(os.path.join(mypath, '..' ,'..', '..')))
|
||||
|
||||
# test the plugin manager with some plugins in the test_plugins directory
|
||||
class TestPluginManager:
|
||||
def test_init(self):
|
||||
self.p = PluginManager(u'./testplugins')
|
||||
p = self.p
|
||||
p.find_plugins(u'./testplugins', None, None)
|
||||
assert(len(p.plugins) == 2)
|
||||
# get list of the names of the plugins
|
||||
names = [plugin.name for plugin in p.plugins]
|
||||
# see which ones we've got
|
||||
assert(u'testplugin1' in names)
|
||||
assert(u'testplugin2' in names)
|
||||
# and not got - it's too deep in the hierarchy!
|
||||
assert(u'testplugin3' not in names)
|
||||
# test that the weighting is done right
|
||||
assert(p.plugins[0].name == "testplugin2")
|
||||
assert(p.plugins[1].name == "testplugin1")
|
||||
|
||||
if __name__ == "__main__":
|
||||
log.debug(u'Starting')
|
||||
t = TestPluginManager()
|
||||
t.test_init()
|
||||
log.debug(u'List of plugins found:')
|
||||
for plugin in t.p.plugins:
|
||||
log.debug(u'Plugin %s, name=%s (version=%d)' %(unicode(plugin),
|
||||
plugin.name, plugin.version))
|
@ -1,241 +0,0 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
# vim: autoindent shiftwidth=4 expandtab textwidth=80 tabstop=4 softtabstop=4
|
||||
|
||||
###############################################################################
|
||||
# OpenLP - Open Source Lyrics Projection #
|
||||
# --------------------------------------------------------------------------- #
|
||||
# Copyright (c) 2008-2010 Raoul Snyman #
|
||||
# Portions copyright (c) 2008-2010 Tim Bentley, Jonathan Corwin, Michael #
|
||||
# Gorven, Scott Guerrieri, Christian Richter, Maikel Stuivenberg, Martin #
|
||||
# Thompson, Jon Tibble, Carsten Tinggaard #
|
||||
# --------------------------------------------------------------------------- #
|
||||
# This program is free software; you can redistribute it and/or modify it #
|
||||
# under the terms of the GNU General Public License as published by the Free #
|
||||
# Software Foundation; version 2 of the License. #
|
||||
# #
|
||||
# This program is distributed in the hope that it will be useful, but WITHOUT #
|
||||
# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or #
|
||||
# FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for #
|
||||
# more details. #
|
||||
# #
|
||||
# You should have received a copy of the GNU General Public License along #
|
||||
# with this program; if not, write to the Free Software Foundation, Inc., 59 #
|
||||
# Temple Place, Suite 330, Boston, MA 02111-1307 USA #
|
||||
###############################################################################
|
||||
|
||||
import sys
|
||||
import os
|
||||
import os.path
|
||||
|
||||
from PyQt4 import QtGui, QtCore
|
||||
|
||||
from openlp.core.theme import Theme
|
||||
from openlp.core.lib import Renderer
|
||||
|
||||
mypath = os.path.split(os.path.abspath(__file__))[0]
|
||||
sys.path.insert(0, (os.path.join(mypath, '..', '..', '..')))
|
||||
|
||||
# from http://aspn.activestate.com/ASPN/Cookbook/Python/Recipe/66062
|
||||
def whoami(depth=1):
|
||||
return sys._getframe(depth).f_code.co_name
|
||||
|
||||
class TstFrame:
|
||||
# {{{ init
|
||||
|
||||
def __init__(self, size):
|
||||
"""Create the DemoPanel."""
|
||||
self.width = size.width();
|
||||
self.height = size.height();
|
||||
# create something to be painted into
|
||||
self._Buffer = QtGui.QPixmap(self.width, self.height)
|
||||
def GetPixmap(self):
|
||||
return self._Buffer
|
||||
|
||||
# }}}
|
||||
|
||||
class TestRender_base:
|
||||
def __init__(self):
|
||||
if not os.path.exists(u'test_results'):
|
||||
os.mkdir(u'test_results')
|
||||
self.app = None
|
||||
def write_to_file(self, pixmap, name):
|
||||
im=pixmap.toImage()
|
||||
testpathname = os.path.join(u'test_results', name+'.bmp')
|
||||
if os.path.exists(testpathname):
|
||||
os.unlink(testpathname)
|
||||
im.save(testpathname, 'bmp')
|
||||
return im
|
||||
# xxx quitting the app still leaves it hanging aroudn so we die
|
||||
# when trying to start another one. Not quitting doesn't help
|
||||
# though This means that the py.test runs both test modules in
|
||||
# sequence and the second one tries to create another application
|
||||
# which gives us errors :(
|
||||
|
||||
def setup_class(self):
|
||||
print "class setup", self
|
||||
try:
|
||||
if self.app is None:
|
||||
pass
|
||||
except AttributeError: # didn't have one
|
||||
print "No app"
|
||||
self.app = None
|
||||
|
||||
print "Test app (should be None)"
|
||||
if self.app is None:
|
||||
print "App is None"
|
||||
self.app = QtGui.QApplication([])
|
||||
else:
|
||||
print "class setup, app is", app
|
||||
# self.app = QtGui.QApplication([])
|
||||
|
||||
def teardown_class(self):
|
||||
print "class quit", self, self.app
|
||||
self.app.quit()
|
||||
|
||||
def setup_method(self, method):
|
||||
print "SSsetup", method
|
||||
if not hasattr(self, 'app'):
|
||||
self.app = None
|
||||
try: # see if we already have an app for some reason.
|
||||
# have to try and so something, cant just test against None
|
||||
print "app", self.app, ";;;"
|
||||
print self.app.quit()
|
||||
print "quitted"
|
||||
except RuntimeError: # not valid app, create one
|
||||
print "Runtime error"
|
||||
except AttributeError: # didn't have one
|
||||
print "Attribute error"
|
||||
# print "App", self.app
|
||||
# self.app = QtGui.QApplication([])
|
||||
print "Application created and sorted"
|
||||
self.size = QtCore.QSize(800,600)
|
||||
frame = TstFrame(size = self.size)
|
||||
self.frame = frame
|
||||
self.paintdest = frame.GetPixmap()
|
||||
self.renderer = Renderer()
|
||||
self.renderer.set_paint_dest(self.paintdest)
|
||||
self.expected_answer = "Don't know yet"
|
||||
self.answer = None
|
||||
print "--------------- Setup Done -------------"
|
||||
|
||||
def teardown_method(self, method):
|
||||
self.write_to_file(self.frame.GetPixmap(), 'test_render')
|
||||
|
||||
class TestRender(TestRender_base):
|
||||
def __init__(self):
|
||||
TestRender_base.__init__(self)
|
||||
|
||||
def setup_method(self, method):
|
||||
TestRender_base.setup_method(self, method)
|
||||
self.renderer.set_debug(1)
|
||||
themefile = os.path.abspath(u'data_for_tests/render_theme.xml')
|
||||
self.renderer.set_theme(Theme(themefile)) # set default theme
|
||||
self.renderer._render_background()
|
||||
self.renderer.set_text_rectangle(QtCore.QRect(
|
||||
0,0, self.size.width()-1, self.size.height()-1))
|
||||
self.msg = None
|
||||
|
||||
def test_easy(self):
|
||||
answer = self.renderer._render_single_line(
|
||||
u'Test line', tlcorner = (0,100))
|
||||
assert(answer == (219,163))
|
||||
|
||||
def test_longer(self):
|
||||
answer = self.renderer._render_single_line(
|
||||
u'Test line with more words than fit on one line',
|
||||
tlcorner = (10,10))
|
||||
assert(answer == (753,136))
|
||||
|
||||
def test_even_longer(self):
|
||||
answer = self.renderer._render_single_line(
|
||||
u'Test line with more words than fit on either one or two lines',
|
||||
tlcorner = (10,10))
|
||||
assert(answer == (753,199))
|
||||
def test_lines(self):
|
||||
lines = []
|
||||
lines.append(u'Line One')
|
||||
lines.append(u'Line Two')
|
||||
lines.append(u'Line Three and should be long enough to wrap')
|
||||
lines.append(u'Line Four and should be long enough to wrap also')
|
||||
answer = self.renderer._render_lines(lines)
|
||||
assert(answer == QtCore.QRect(0,0,741,378))
|
||||
|
||||
def test_set_words_openlp(self):
|
||||
words="""
|
||||
Verse 1: Line 1
|
||||
Line 2
|
||||
|
||||
Verse 2: Line 1
|
||||
Line 2
|
||||
|
||||
Verse 3: Line 1
|
||||
Line 2
|
||||
Line 3"""
|
||||
expected_answer = ["Verse 1: Line 1\nLine 2","Verse 2: Line 1\nLine 2","Verse 3: Line 1\nLine 2\nLine 3"]
|
||||
answer = self.renderer.set_words_openlp(words)
|
||||
assert(answer == expected_answer)
|
||||
|
||||
def test_render_screens(self):
|
||||
words="""
|
||||
Verse 1: Line 1
|
||||
Line 2
|
||||
|
||||
Verse 2: Line 1
|
||||
Line 2
|
||||
|
||||
Verse 3: Line 1
|
||||
Line 2
|
||||
Line 3"""
|
||||
verses = self.renderer.set_words_openlp(words)
|
||||
expected_answer = ["Verse 1: Line 1\nLine 2","Verse 2: Line 1\nLine 2","Verse 3: Line 1\nLine 2\nLine 3"]
|
||||
assert(verses == expected_answer)
|
||||
|
||||
expected_answer = [QtCore.QRect(0,0,397,126), QtCore.QRect(0,0,397,126),
|
||||
QtCore.QRect(0,0,397,189)]
|
||||
for v in range(len(verses)):
|
||||
answer=self.renderer.render_screen(v)
|
||||
# print v, answer.x(), answer.y(), answer.width(), answer.height()
|
||||
assert(answer == expected_answer[v])
|
||||
|
||||
def split_test(self, number, answer, expected_answers):
|
||||
lines=[]
|
||||
print "Split test", number, answer
|
||||
for i in range(number):
|
||||
extra=""
|
||||
if i == 51: # make an extra long line on line 51 to test wrapping
|
||||
extra = "Some more words to make it wrap around don't you know until it wraps so many times we don't know what to do"
|
||||
lines.append(u'Line %d %s' % (i, extra))
|
||||
result = self.renderer.split_set_of_lines(lines)
|
||||
print "results---------------__", result
|
||||
for i in range(len(result)):
|
||||
self.setup_method(None)
|
||||
answer = self.renderer._render_lines(result[i])
|
||||
print answer
|
||||
self.write_to_file(self.frame.GetPixmap(), "split_test_%03d"% i)
|
||||
print number, i, answer.x(), answer.y(), answer.width(), \
|
||||
answer.height()
|
||||
e = expected_answers[i]
|
||||
assert(answer == QtCore.QRect(e[0],e[1],e[2],e[3]))
|
||||
|
||||
|
||||
def test_splits(self):
|
||||
print "Test splits"
|
||||
self.split_test(100, 11, [(0,0,180,567), (0,0,214,567), (0,0,214,567),
|
||||
(0,0,214,567), (0,0,214,567), (0,0,214,378), (0,0,759,567),
|
||||
(0,0,214,567), (0,0,214,567), (0,0,214,567), (0,0,214,567),
|
||||
(0,0,214,567), (0,0,214,567)])
|
||||
self.split_test(30, 4, [ (0,0,180,441), (0,0,214,441), (0,0,214,441),
|
||||
(0,0,214,441)])
|
||||
self.split_test(20, 3, [(0,0,180,378), (0,0,214,378), (0,0,214,378)])
|
||||
self.split_test(12, 2, [(0,0,180,378), (0,0,214,378)])
|
||||
self.split_test(4, 1, [(0,0,180,252)])
|
||||
self.split_test(6, 1, [(0,0,180,378)])
|
||||
self.split_test(8, 1, [(0,0,180,504)])
|
||||
|
||||
if __name__ == "__main__":
|
||||
t = TestRender()
|
||||
t.setup_class()
|
||||
t.setup_method(None)
|
||||
t.test_easy()
|
||||
t.test_splits()
|
||||
t.teardown_method(None)
|
@ -1,319 +0,0 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
# vim: autoindent shiftwidth=4 expandtab textwidth=80 tabstop=4 softtabstop=4
|
||||
|
||||
###############################################################################
|
||||
# OpenLP - Open Source Lyrics Projection #
|
||||
# --------------------------------------------------------------------------- #
|
||||
# Copyright (c) 2008-2010 Raoul Snyman #
|
||||
# Portions copyright (c) 2008-2010 Tim Bentley, Jonathan Corwin, Michael #
|
||||
# Gorven, Scott Guerrieri, Christian Richter, Maikel Stuivenberg, Martin #
|
||||
# Thompson, Jon Tibble, Carsten Tinggaard #
|
||||
# --------------------------------------------------------------------------- #
|
||||
# This program is free software; you can redistribute it and/or modify it #
|
||||
# under the terms of the GNU General Public License as published by the Free #
|
||||
# Software Foundation; version 2 of the License. #
|
||||
# #
|
||||
# This program is distributed in the hope that it will be useful, but WITHOUT #
|
||||
# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or #
|
||||
# FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for #
|
||||
# more details. #
|
||||
# #
|
||||
# You should have received a copy of the GNU General Public License along #
|
||||
# with this program; if not, write to the Free Software Foundation, Inc., 59 #
|
||||
# Temple Place, Suite 330, Boston, MA 02111-1307 USA #
|
||||
###############################################################################
|
||||
|
||||
import sys
|
||||
import os
|
||||
|
||||
from PyQt4 import QtGui, QtCore
|
||||
|
||||
from openlp.core.theme import Theme
|
||||
from test_render import TestRender_base, whoami
|
||||
|
||||
pypath = os.path.split(os.path.abspath(__file__))[0]
|
||||
sys.path.insert(0, (os.path.join(mypath, '..', '..', '..')))
|
||||
|
||||
def compare_images(goldenim, testim, threshold=0.01):
|
||||
# easy test first
|
||||
if goldenim == testim:
|
||||
return 1
|
||||
# how close are they? Calculated the sum of absolute differences in
|
||||
# each channel of each pixel and divide by the number of pixels in the image
|
||||
# if this sum is < threshold, the images are deemed to be "close enough"
|
||||
sad = 0;
|
||||
for x in range(goldenim.width()):
|
||||
for y in range(goldenim.height()):
|
||||
p1=goldenim.pixel(x,y)
|
||||
p2=testim.pixel(x,y)
|
||||
sad += abs((p1&0xFF)-(p2&0xFF))
|
||||
sad += abs((p1>>8&0xFF)-(p2>>8&0xFF))
|
||||
sad += abs((p1>>16&0xFF)-(p2>>16&0xFF))
|
||||
sad /= float(goldenim.width()*goldenim.height())
|
||||
if (sad < threshold):
|
||||
return 1
|
||||
return 0
|
||||
|
||||
class TestRenderTheme(TestRender_base):
|
||||
# {{{ Basics
|
||||
|
||||
def __init__(self):
|
||||
TestRender_base.__init__(self)
|
||||
|
||||
def setup_method(self, method):
|
||||
TestRender_base.setup_method(self, method)
|
||||
print "Theme setup", method
|
||||
# print "setup theme"
|
||||
self.renderer.set_theme(Theme(u'blank_theme.xml')) # set "blank" theme
|
||||
self.renderer.set_text_rectangle(QtCore.QRect(0,0, self.size.width(),
|
||||
self.size.height()))
|
||||
words = """How sweet the name of Jesus sounds
|
||||
In a believer's ear!
|
||||
It soothes his sorrows, heals his wounds,
|
||||
And drives away his fear.
|
||||
"""
|
||||
verses = self.renderer.set_words_openlp(words)
|
||||
# usually the same
|
||||
self.expected_answer = QtCore.QRect(0, 0, 559, 342)
|
||||
self.msg = None
|
||||
self.bmpname = "Not set a bitmap yet"
|
||||
print "------------- setup done --------------"
|
||||
|
||||
def teardown_method(self, method):
|
||||
print "============ teardown =============", method, self.bmpname
|
||||
if self.bmpname is not None:
|
||||
assert (self.compare_DC_to_file(self.bmpname))
|
||||
if self.expected_answer is not None: # result=None => Nothing to check
|
||||
assert self.expected_answer == self.answer
|
||||
print "============ teardown done ========="
|
||||
|
||||
def compare_DC_to_file(self, name):
|
||||
"""writes DC out to a bitmap file and then compares it with a golden
|
||||
one returns True if OK, False if not (so you can assert on it)
|
||||
|
||||
"""
|
||||
print "--- compare DC to file --- ", name
|
||||
p = self.frame.GetPixmap()
|
||||
im = self.write_to_file(p, name)
|
||||
print "Compare"
|
||||
goldenfilename=os.path.join(u'golden_bitmaps",name+".bmp')
|
||||
if os.path.exists(goldenfilename):
|
||||
goldenim = QtGui.QImage(goldenfilename)
|
||||
else:
|
||||
print "File", goldenfilename, "not found"
|
||||
return False
|
||||
if (compare_images(goldenim, im)):
|
||||
print name, "Images match"
|
||||
return True
|
||||
else:
|
||||
print name, goldenfilename, "Images don't match"
|
||||
return False
|
||||
|
||||
def test_theme_basic(self):
|
||||
self.answer = self.renderer.render_screen(0)
|
||||
self.bmpname = whoami()
|
||||
print self.renderer._theme.FontProportion
|
||||
print self.answer, self.expected_answer, \
|
||||
self.answer == self.expected_answer
|
||||
# self.msg=self.bmpname
|
||||
|
||||
# }}}
|
||||
|
||||
# {{{ Gradients
|
||||
def test_gradient_h(self):
|
||||
# normally we wouldn't hack with these directly!
|
||||
self.renderer._theme.BackgroundType = 1
|
||||
self.renderer._theme.BackgroundParameter1 = QtGui.QColor(255,0,0)
|
||||
self.renderer._theme.BackgroundParameter2 = QtGui.QColor(255,255,0)
|
||||
self.renderer._theme.BackgroundParameter3 = 1
|
||||
self.answer = self.renderer.render_screen(0)
|
||||
self.bmpname = whoami()
|
||||
|
||||
def test_gradient_v(self):
|
||||
# normally we wouldn't hack with these directly!
|
||||
self.renderer._theme.BackgroundType = 1
|
||||
self.renderer._theme.BackgroundParameter1 = QtGui.QColor(255,0,0)
|
||||
self.renderer._theme.BackgroundParameter2 = QtGui.QColor(255,255,0)
|
||||
self.renderer._theme.BackgroundParameter3 = 0
|
||||
self.answer = self.renderer.render_screen(0)
|
||||
self.bmpname = whoami()
|
||||
# }}}
|
||||
|
||||
# {{{ backgrounds
|
||||
def test_bg_stretch_y(self):
|
||||
t = Theme(u'blank_theme.xml')
|
||||
t.BackgroundType = 2
|
||||
t.BackgroundParameter1 = os.path.join(u'data_for_tests',
|
||||
'snowsmall.jpg')
|
||||
t.BackgroundParameter2 = QtGui.QColor(0,0,64)
|
||||
t.BackgroundParameter3 = 0
|
||||
t.Name = "stretch y"
|
||||
self.renderer.set_theme(t)
|
||||
print "render"
|
||||
self.answer = self.renderer.render_screen(0)
|
||||
print "whoami"
|
||||
self.bmpname = whoami()
|
||||
print "fone"
|
||||
|
||||
def test_bg_shrink_y(self):
|
||||
t = Theme(u'blank_theme.xml')
|
||||
t.BackgroundType = 2
|
||||
t.BackgroundParameter1 = os.path.join(u'data_for_tests', 'snowbig.jpg')
|
||||
t.BackgroundParameter2 = QtGui.QColor(0,0,64)
|
||||
t.BackgroundParameter3 = 0
|
||||
t.Name = "shrink y"
|
||||
self.renderer.set_theme(t)
|
||||
self.answer = self.renderer.render_screen(0)
|
||||
self.bmpname = whoami()
|
||||
|
||||
def test_bg_stretch_x(self):
|
||||
t = Theme(u'blank_theme.xml')
|
||||
t.BackgroundType = 2
|
||||
t.BackgroundParameter1 = os.path.join(u'data_for_tests',
|
||||
'treessmall.jpg')
|
||||
t.BackgroundParameter2 = QtGui.QColor(0,0,64)
|
||||
t.BackgroundParameter3 = 0
|
||||
t.VerticalAlign = 2
|
||||
t.Name = "stretch x"
|
||||
self.renderer.set_theme(t)
|
||||
self.answer = self.renderer.render_screen(0)
|
||||
self.expected_answer = QtCore.QRect(0, 129, 559, 342)
|
||||
self.bmpname = whoami()
|
||||
|
||||
def test_bg_shrink_x(self):
|
||||
t = Theme(u'blank_theme.xml')
|
||||
t.BackgroundType = 2
|
||||
t.BackgroundParameter1 = os.path.join(u'data_for_tests',
|
||||
'treesbig.jpg')
|
||||
t.BackgroundParameter2 = QtGui.QColor(0,0,64)
|
||||
t.BackgroundParameter3 = 0
|
||||
t.VerticalAlign = 2
|
||||
t.Name = "shrink x"
|
||||
self.renderer.set_theme(t)
|
||||
self.expected_answer = QtCore.QRect(0, 129, 559, 342)
|
||||
self.answer = self.renderer.render_screen(0)
|
||||
self.bmpname = whoami()
|
||||
# }}}
|
||||
|
||||
# {{{ Vertical alignment
|
||||
def test_theme_vertical_align_top(self):
|
||||
t = Theme(u'blank_theme.xml')
|
||||
t.BackgroundType = 0
|
||||
t.BackgroundParameter1 = QtGui.QColor(0,0,64)
|
||||
t.VerticalAlign = 0
|
||||
t.Name = "valign top"
|
||||
self.renderer.set_theme(t)
|
||||
self.answer = self.renderer.render_screen(0)
|
||||
self.bmpname = whoami()
|
||||
|
||||
def test_theme_vertical_align_bot(self):
|
||||
t = Theme(u'blank_theme.xml')
|
||||
t.BackgroundType = 0
|
||||
t.BackgroundParameter1 = QtGui.QColor(0,0,64)
|
||||
t.VerticalAlign = 1
|
||||
t.Name = "valign bot"
|
||||
self.renderer.set_theme(t)
|
||||
self.answer = self.renderer.render_screen(0)
|
||||
self.expected_answer = QtCore.QRect(0, 257, 559, 342)
|
||||
self.bmpname = whoami()
|
||||
|
||||
def test_theme_vertical_align_cen(self):
|
||||
t = Theme(u'blank_theme.xml')
|
||||
t.BackgroundType = 0
|
||||
t.BackgroundParameter1 = QtGui.QColor(0,0,64)
|
||||
t.VerticalAlign = 2
|
||||
t.Name = "valign cen"
|
||||
self.renderer.set_theme(t)
|
||||
self.answer = self.renderer.render_screen(0)
|
||||
self.expected_answer = QtCore.QRect(0, 129, 559, 342)
|
||||
self.bmpname = whoami()
|
||||
# }}}
|
||||
|
||||
# {{{ Horzontal alignment
|
||||
def test_theme_horizontal_align_left(self):
|
||||
t = Theme(u'blank_theme.xml')
|
||||
t.BackgroundType = 0
|
||||
t.BackgroundParameter1 = QtGui.QColor(0,0,64)
|
||||
t.VerticalAlign = 0
|
||||
t.HorizontalAlign = 0
|
||||
t.Name = "halign left"
|
||||
self.renderer.set_theme(t)
|
||||
self.answer = self.renderer.render_screen(0)
|
||||
self.bmpname = whoami()
|
||||
|
||||
def test_theme_horizontal_align_right(self):
|
||||
t = Theme(u'blank_theme.xml')
|
||||
t.BackgroundType = 0
|
||||
t.BackgroundParameter1 = QtGui.QColor(0,0,64)
|
||||
t.VerticalAlign = 0
|
||||
t.HorizontalAlign = 1
|
||||
t.Name = "halign right"
|
||||
self.renderer.set_theme(t)
|
||||
self.expected_answer = QtCore.QRect(0, 0, 800, 342)
|
||||
self.answer = self.renderer.render_screen(0)
|
||||
self.bmpname = whoami()
|
||||
|
||||
def test_theme_horizontal_align_centre(self):
|
||||
t = Theme(u'blank_theme.xml')
|
||||
t.BackgroundType = 0
|
||||
t.BackgroundParameter1 = QtGui.QColor(0,0,64)
|
||||
t.VerticalAlign = 0
|
||||
t.HorizontalAlign = 2
|
||||
t.Name = "halign centre"
|
||||
self.renderer.set_theme(t)
|
||||
self.answer = self.renderer.render_screen(0)
|
||||
self.expected_answer = QtCore.QRect(0, 0, 679, 342)
|
||||
self.bmpname = whoami()
|
||||
|
||||
def test_theme_horizontal_align_left_lyric(self):
|
||||
t = Theme(u'blank_theme.xml')
|
||||
t.BackgroundType = 0
|
||||
t.BackgroundParameter1 = QtGui.QColor(0,0,64)
|
||||
t.VerticalAlign = 0
|
||||
t.HorizontalAlign = 0
|
||||
t.WrapStyle = 1
|
||||
t.Name = "halign left lyric"
|
||||
self.renderer.set_theme(t)
|
||||
self.answer = self.renderer.render_screen(0)
|
||||
self.expected_answer = QtCore.QRect(0, 0, 778, 342)
|
||||
self.bmpname = whoami()
|
||||
# }}}
|
||||
|
||||
# {{{ Shadows and outlines
|
||||
def test_theme_shadow_outline(self):
|
||||
t = Theme(u'blank_theme.xml')
|
||||
|
||||
t.BackgroundType = 0
|
||||
t.BackgroundParameter1 = QtGui.QColor(0,0,0);
|
||||
t.Name="shadow/outline"
|
||||
t.Shadow = 1
|
||||
t.Outline = 1
|
||||
t.ShadowColor = QtGui.QColor(64,128,0)
|
||||
t.OutlineColor = QtGui.QColor(128,0,0)
|
||||
self.renderer.set_debug(1)
|
||||
self.renderer.set_theme(t)
|
||||
self.answer = self.renderer.render_screen(0)
|
||||
hoffset = self.renderer._shadow_offset+2*(self.renderer._outline_offset)
|
||||
voffset = hoffset * (len(self.renderer.words[0])+1)
|
||||
|
||||
self.expected_answer = QtCore.QRect(0, 0, 559+hoffset, 342+voffset)
|
||||
self.bmpname = whoami()
|
||||
# }}}
|
||||
|
||||
def test_theme_font(self):
|
||||
t = Theme(u'blank_theme.xml')
|
||||
t.BackgroundType = 0
|
||||
t.BackgroundParameter1 = QtGui.QColor(0,0,64)
|
||||
t.Name = "font"
|
||||
t.FontName = "Times New Roman"
|
||||
self.renderer.set_theme(t)
|
||||
self.answer = self.renderer.render_screen(0)
|
||||
self.expected_answer = QtCore.QRect(0, 0, 499, 336)
|
||||
self.bmpname=whoami()
|
||||
|
||||
if __name__ == "__main__":
|
||||
test_render_theme = TestRenderTheme()
|
||||
test_render_theme.setup_class()
|
||||
test_render_theme.setup_method(None)
|
||||
test_render_theme.test_bg_stretch_y()
|
||||
test_render_theme.teardown_method(None)
|
@ -1 +0,0 @@
|
||||
|
@ -1 +0,0 @@
|
||||
|
@ -1,13 +0,0 @@
|
||||
from openlp.core.lib import Plugin
|
||||
import logging
|
||||
|
||||
class testplugin3toodeep(Plugin):
|
||||
name="testplugin3"
|
||||
version=0
|
||||
global log
|
||||
log=logging.getLogger(u'testplugin1')
|
||||
log.info(u'Started')
|
||||
weight=10
|
||||
def __init__(self):
|
||||
pass
|
||||
|
@ -1,13 +0,0 @@
|
||||
from openlp.core.lib import Plugin
|
||||
import logging
|
||||
|
||||
class testplugin1(Plugin):
|
||||
name="testplugin1"
|
||||
version=0
|
||||
global log
|
||||
log=logging.getLogger(u'testplugin1')
|
||||
log.info(u'Started')
|
||||
weight=10
|
||||
def __init__(self):
|
||||
pass
|
||||
|
@ -1,8 +0,0 @@
|
||||
from openlp.core.lib import Plugin
|
||||
|
||||
class testplugin2(Plugin):
|
||||
name="testplugin2"
|
||||
version=1
|
||||
weight=1
|
||||
def __init__(self):
|
||||
pass
|
@ -1,82 +0,0 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
# vim: autoindent shiftwidth=4 expandtab textwidth=80 tabstop=4 softtabstop=4
|
||||
|
||||
###############################################################################
|
||||
# OpenLP - Open Source Lyrics Projection #
|
||||
# --------------------------------------------------------------------------- #
|
||||
# Copyright (c) 2008-2010 Raoul Snyman #
|
||||
# Portions copyright (c) 2008-2010 Tim Bentley, Jonathan Corwin, Michael #
|
||||
# Gorven, Scott Guerrieri, Christian Richter, Maikel Stuivenberg, Martin #
|
||||
# Thompson, Jon Tibble, Carsten Tinggaard #
|
||||
# --------------------------------------------------------------------------- #
|
||||
# This program is free software; you can redistribute it and/or modify it #
|
||||
# under the terms of the GNU General Public License as published by the Free #
|
||||
# Software Foundation; version 2 of the License. #
|
||||
# #
|
||||
# This program is distributed in the hope that it will be useful, but WITHOUT #
|
||||
# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or #
|
||||
# FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for #
|
||||
# more details. #
|
||||
# #
|
||||
# You should have received a copy of the GNU General Public License along #
|
||||
# with this program; if not, write to the Free Software Foundation, Inc., 59 #
|
||||
# Temple Place, Suite 330, Boston, MA 02111-1307 USA #
|
||||
###############################################################################
|
||||
|
||||
import os
|
||||
import os.path
|
||||
import sys
|
||||
|
||||
from PyQt4 import QtGui
|
||||
|
||||
from openlp.core.theme import Theme
|
||||
|
||||
mypath = os.path.split(os.path.abspath(__file__))[0]
|
||||
sys.path.insert(0, (os.path.join(mypath, '..', '..', '..', '..')))
|
||||
|
||||
print sys.path
|
||||
|
||||
def test_read_theme():
|
||||
dir = os.path.split(__file__)[0]
|
||||
# test we can read a theme
|
||||
theme = Theme(os.path.join(dir, 'test_theme.xml'))
|
||||
print theme
|
||||
assert(theme.BackgroundParameter1 == 'sunset1.jpg')
|
||||
assert(theme.BackgroundParameter2 is None)
|
||||
assert(theme.BackgroundParameter3 is None)
|
||||
assert(theme.BackgroundType == 2)
|
||||
assert(theme.FontColor == QtGui.QColor(255,255,255))
|
||||
assert(theme.FontName == 'Tahoma')
|
||||
assert(theme.FontProportion == 16)
|
||||
assert(theme.FontUnits == 'pixels')
|
||||
assert(theme.HorizontalAlign == 2)
|
||||
assert(theme.Name == 'openlp.org Packaged Theme')
|
||||
assert(theme.Outline == -1)
|
||||
assert(theme.OutlineColor == QtGui.QColor(255,0,0))
|
||||
assert(theme.Shadow == -1)
|
||||
assert(theme.ShadowColor == QtGui.QColor(0,0,1))
|
||||
assert(theme.VerticalAlign == 0)
|
||||
|
||||
def test_theme():
|
||||
# test we create a "blank" theme correctly
|
||||
theme = Theme()
|
||||
print theme
|
||||
assert(theme.BackgroundParameter1 == QtGui.QColor(0,0,0))
|
||||
assert(theme.BackgroundParameter2 is None)
|
||||
assert(theme.BackgroundParameter3 is None)
|
||||
assert(theme.BackgroundType == 0)
|
||||
assert(theme.FontColor == QtGui.QColor(255,255,255))
|
||||
assert(theme.FontName == 'Arial')
|
||||
assert(theme.FontProportion == 30)
|
||||
assert(theme.HorizontalAlign == 0)
|
||||
assert(theme.FontUnits == 'pixels')
|
||||
assert(theme.Name == 'BlankStyle')
|
||||
assert(theme.Outline == 0)
|
||||
assert(theme.Shadow == 0)
|
||||
assert(theme.VerticalAlign == 0)
|
||||
|
||||
print "Tests passed"
|
||||
|
||||
if __name__ == "__main__":
|
||||
test_read_theme()
|
||||
test_theme()
|
@ -1,18 +0,0 @@
|
||||
<?xml version="1.0" encoding="iso-8859-1"?>
|
||||
<Theme>
|
||||
<Name>openlp.org Packaged Theme</Name>
|
||||
<BackgroundType>2</BackgroundType>
|
||||
<BackgroundParameter1>sunset1.jpg</BackgroundParameter1>
|
||||
<BackgroundParameter2/>
|
||||
<BackgroundParameter3/>
|
||||
<FontName>Tahoma</FontName>
|
||||
<FontColor>clWhite</FontColor>
|
||||
<FontProportion>16</FontProportion>
|
||||
<FontUnits>pixels</FontUnits>
|
||||
<Shadow>-1</Shadow>
|
||||
<ShadowColor>$00000001</ShadowColor>
|
||||
<Outline>-1</Outline>
|
||||
<OutlineColor>clRed</OutlineColor>
|
||||
<HorizontalAlign>2</HorizontalAlign>
|
||||
<VerticalAlign>0</VerticalAlign>
|
||||
</Theme>
|
@ -23,14 +23,27 @@
|
||||
# Temple Place, Suite 330, Boston, MA 02111-1307 USA #
|
||||
###############################################################################
|
||||
|
||||
class HideMode(object):
|
||||
"""
|
||||
This is basically an enumeration class which specifies the mode of a Bible.
|
||||
Mode refers to whether or not a Bible in OpenLP is a full Bible or needs to
|
||||
be downloaded from the Internet on an as-needed basis.
|
||||
"""
|
||||
Blank = 1
|
||||
Theme = 2
|
||||
Screen = 3
|
||||
|
||||
from slidecontroller import HideMode
|
||||
from servicenoteform import ServiceNoteForm
|
||||
from serviceitemeditform import ServiceItemEditForm
|
||||
from screen import ScreenList
|
||||
from maindisplay import MainDisplay
|
||||
from maindisplay import VideoDisplay
|
||||
from maindisplay import DisplayManager
|
||||
from amendthemeform import AmendThemeForm
|
||||
from slidecontroller import SlideController
|
||||
from splashscreen import SplashScreen
|
||||
from displaytab import DisplayTab
|
||||
from generaltab import GeneralTab
|
||||
from themestab import ThemesTab
|
||||
from aboutform import AboutForm
|
||||
|
@ -24,6 +24,7 @@
|
||||
###############################################################################
|
||||
|
||||
from PyQt4 import QtCore, QtGui
|
||||
from openlp.core.lib import translate
|
||||
|
||||
class Ui_AboutDialog(object):
|
||||
def setupUi(self, AboutDialog):
|
||||
@ -113,8 +114,8 @@ class Ui_AboutDialog(object):
|
||||
QtCore.QMetaObject.connectSlotsByName(AboutDialog)
|
||||
|
||||
def retranslateUi(self, AboutDialog):
|
||||
AboutDialog.setWindowTitle(self.trUtf8('About OpenLP'))
|
||||
self.AboutTextEdit.setPlainText(self.trUtf8(
|
||||
AboutDialog.setWindowTitle(translate('AboutForm', 'About OpenLP'))
|
||||
self.AboutTextEdit.setPlainText(translate('AboutForm',
|
||||
'OpenLP <version><revision> - Open Source Lyrics '
|
||||
'Projection\n'
|
||||
'\n'
|
||||
@ -131,8 +132,8 @@ class Ui_AboutDialog(object):
|
||||
'consider contributing by using the button below.'
|
||||
))
|
||||
self.AboutNotebook.setTabText(
|
||||
self.AboutNotebook.indexOf(self.AboutTab), self.trUtf8('About'))
|
||||
self.CreditsTextEdit.setPlainText(self.trUtf8(
|
||||
self.AboutNotebook.indexOf(self.AboutTab), translate('AboutForm', 'About'))
|
||||
self.CreditsTextEdit.setPlainText(translate('AboutForm',
|
||||
'Project Lead\n'
|
||||
' Raoul "superfly" Snyman\n'
|
||||
'\n'
|
||||
@ -164,11 +165,10 @@ class Ui_AboutDialog(object):
|
||||
))
|
||||
self.AboutNotebook.setTabText(
|
||||
self.AboutNotebook.indexOf(self.CreditsTab),
|
||||
self.trUtf8('Credits'))
|
||||
self.LicenseTextEdit.setPlainText(self.trUtf8(
|
||||
'Copyright ' + u'\u00a9'.encode('utf8') + ' 2004-2010 Raoul '
|
||||
'Snyman\n'
|
||||
'Portions copyright ' + u'\u00a9'.encode('utf8') + ' 2004-2010 '
|
||||
translate('AboutForm', 'Credits'))
|
||||
self.LicenseTextEdit.setPlainText(translate('AboutForm',
|
||||
'Copyright \xa9 2004-2010 Raoul Snyman\n'
|
||||
'Portions copyright \xa9 2004-2010 '
|
||||
'Tim Bentley, Jonathan Corwin, Michael Gorven, Scott Guerrieri, '
|
||||
'Christian Richter, Maikel Stuivenberg, Martin Thompson, Jon '
|
||||
'Tibble, Carsten Tinggaard\n'
|
||||
@ -557,6 +557,6 @@ class Ui_AboutDialog(object):
|
||||
'instead of this License.'))
|
||||
self.AboutNotebook.setTabText(
|
||||
self.AboutNotebook.indexOf(self.LicenseTab),
|
||||
self.trUtf8('License'))
|
||||
self.ContributeButton.setText(self.trUtf8('Contribute'))
|
||||
self.CloseButton.setText(self.trUtf8('Close'))
|
||||
translate('AboutForm', 'License'))
|
||||
self.ContributeButton.setText(translate('AboutForm', 'Contribute'))
|
||||
self.CloseButton.setText(translate('AboutForm', 'Close'))
|
||||
|
@ -25,6 +25,7 @@
|
||||
|
||||
from PyQt4 import QtCore, QtGui
|
||||
from openlp.core.lib import build_icon
|
||||
from openlp.core.lib import translate
|
||||
|
||||
class Ui_AmendThemeDialog(object):
|
||||
def setupUi(self, AmendThemeDialog):
|
||||
@ -178,16 +179,23 @@ class Ui_AmendThemeDialog(object):
|
||||
self.FontMainWeightLabel.setObjectName("FontMainWeightLabel")
|
||||
self.MainFontLayout.setWidget(3, QtGui.QFormLayout.LabelRole, self.FontMainWeightLabel)
|
||||
self.MainLeftLayout.addWidget(self.FontMainGroupBox)
|
||||
self.FontMainWrapLineAdjustmentLabel = QtGui.QLabel(self.FontMainGroupBox)
|
||||
self.FontMainWrapLineAdjustmentLabel.setObjectName("FontMainWrapLineAdjustmentLabel")
|
||||
self.MainFontLayout.setWidget(4, QtGui.QFormLayout.LabelRole, self.FontMainWrapLineAdjustmentLabel)
|
||||
self.FontMainLineAdjustmentSpinBox = QtGui.QSpinBox(self.FontMainGroupBox)
|
||||
self.FontMainLineAdjustmentSpinBox.setObjectName("FontMainLineAdjustmentSpinBox")
|
||||
self.FontMainLineAdjustmentSpinBox.setMinimum(-99)
|
||||
self.MainFontLayout.setWidget(4, QtGui.QFormLayout.FieldRole, self.FontMainLineAdjustmentSpinBox)
|
||||
self.FontMainWrapIndentationLabel = QtGui.QLabel(self.FontMainGroupBox)
|
||||
self.FontMainWrapIndentationLabel.setObjectName("FontMainWrapIndentationLabel")
|
||||
self.MainFontLayout.setWidget(4, QtGui.QFormLayout.LabelRole, self.FontMainWrapIndentationLabel)
|
||||
self.MainFontLayout.setWidget(5, QtGui.QFormLayout.LabelRole, self.FontMainWrapIndentationLabel)
|
||||
self.FontMainLineSpacingSpinBox = QtGui.QSpinBox(self.FontMainGroupBox)
|
||||
self.FontMainLineSpacingSpinBox.setObjectName("FontMainLineSpacingSpinBox")
|
||||
self.FontMainLineSpacingSpinBox.setMaximum(10)
|
||||
self.MainFontLayout.setWidget(4, QtGui.QFormLayout.FieldRole, self.FontMainLineSpacingSpinBox)
|
||||
self.MainFontLayout.setWidget(5, QtGui.QFormLayout.FieldRole, self.FontMainLineSpacingSpinBox)
|
||||
self.FontMainLinesPageLabel = QtGui.QLabel(self.FontMainGroupBox)
|
||||
self.FontMainLinesPageLabel.setObjectName("FontMainLinesPageLabel")
|
||||
self.MainFontLayout.setWidget(5, QtGui.QFormLayout.LabelRole, self.FontMainLinesPageLabel)
|
||||
self.MainFontLayout.setWidget(6, QtGui.QFormLayout.LabelRole, self.FontMainLinesPageLabel)
|
||||
spacerItem1 = QtGui.QSpacerItem(20, 40, QtGui.QSizePolicy.Minimum, QtGui.QSizePolicy.Expanding)
|
||||
self.MainLeftLayout.addItem(spacerItem1)
|
||||
self.FontMainLayout.addWidget(self.MainLeftWidget)
|
||||
@ -595,94 +603,95 @@ class Ui_AmendThemeDialog(object):
|
||||
AmendThemeDialog.setTabOrder(self.HorizontalComboBox, self.VerticalComboBox)
|
||||
|
||||
def retranslateUi(self, AmendThemeDialog):
|
||||
AmendThemeDialog.setWindowTitle(self.trUtf8('Theme Maintenance'))
|
||||
self.ThemeNameLabel.setText(self.trUtf8('Theme Name:'))
|
||||
self.BackgroundLabel.setText(self.trUtf8('Background:'))
|
||||
self.BackgroundComboBox.setItemText(0, self.trUtf8('Opaque'))
|
||||
self.BackgroundComboBox.setItemText(1, self.trUtf8('Transparent'))
|
||||
self.BackgroundTypeLabel.setText(self.trUtf8('Background Type:'))
|
||||
self.BackgroundTypeComboBox.setItemText(0, self.trUtf8('Solid Color'))
|
||||
self.BackgroundTypeComboBox.setItemText(1, self.trUtf8('Gradient'))
|
||||
self.BackgroundTypeComboBox.setItemText(2, self.trUtf8('Image'))
|
||||
self.Color1Label.setText(self.trUtf8('<Color1>'))
|
||||
self.Color2Label.setText(self.trUtf8('<Color2>'))
|
||||
self.ImageLabel.setText(self.trUtf8('Image:'))
|
||||
self.GradientLabel.setText(self.trUtf8('Gradient :'))
|
||||
self.GradientComboBox.setItemText(0, self.trUtf8('Horizontal'))
|
||||
self.GradientComboBox.setItemText(1, self.trUtf8('Vertical'))
|
||||
self.GradientComboBox.setItemText(2, self.trUtf8('Circular'))
|
||||
AmendThemeDialog.setWindowTitle(translate('AmendThemeForm', 'Theme Maintenance'))
|
||||
self.ThemeNameLabel.setText(translate('AmendThemeForm', 'Theme Name:'))
|
||||
self.BackgroundLabel.setText(translate('AmendThemeForm', 'Background:'))
|
||||
self.BackgroundComboBox.setItemText(0, translate('AmendThemeForm', 'Opaque'))
|
||||
self.BackgroundComboBox.setItemText(1, translate('AmendThemeForm', 'Transparent'))
|
||||
self.BackgroundTypeLabel.setText(translate('AmendThemeForm', 'Background Type:'))
|
||||
self.BackgroundTypeComboBox.setItemText(0, translate('AmendThemeForm', 'Solid Color'))
|
||||
self.BackgroundTypeComboBox.setItemText(1, translate('AmendThemeForm', 'Gradient'))
|
||||
self.BackgroundTypeComboBox.setItemText(2, translate('AmendThemeForm', 'Image'))
|
||||
self.Color1Label.setText(translate('AmendThemeForm', '<Color1>'))
|
||||
self.Color2Label.setText(translate('AmendThemeForm', '<Color2>'))
|
||||
self.ImageLabel.setText(translate('AmendThemeForm', 'Image:'))
|
||||
self.GradientLabel.setText(translate('AmendThemeForm', 'Gradient :'))
|
||||
self.GradientComboBox.setItemText(0, translate('AmendThemeForm', 'Horizontal'))
|
||||
self.GradientComboBox.setItemText(1, translate('AmendThemeForm', 'Vertical'))
|
||||
self.GradientComboBox.setItemText(2, translate('AmendThemeForm', 'Circular'))
|
||||
self.ThemeTabWidget.setTabText(
|
||||
self.ThemeTabWidget.indexOf(self.BackgroundTab),
|
||||
self.trUtf8('Background'))
|
||||
self.FontMainGroupBox.setTitle(self.trUtf8('Main Font'))
|
||||
self.FontMainlabel.setText(self.trUtf8('Font:'))
|
||||
self.FontMainColorLabel.setText(self.trUtf8('Font Color:'))
|
||||
self.FontMainSize.setText(self.trUtf8('Size:'))
|
||||
self.FontMainSizeSpinBox.setSuffix(self.trUtf8('pt'))
|
||||
self.FontMainWrapIndentationLabel.setText(self.trUtf8('Wrap Indentation'))
|
||||
self.FontMainWeightComboBox.setItemText(0, self.trUtf8('Normal'))
|
||||
self.FontMainWeightComboBox.setItemText(1, self.trUtf8('Bold'))
|
||||
self.FontMainWeightComboBox.setItemText(2, self.trUtf8('Italics'))
|
||||
self.FontMainWeightComboBox.setItemText(3, self.trUtf8('Bold/Italics'))
|
||||
self.FontMainWeightLabel.setText(self.trUtf8('Font Weight:'))
|
||||
self.MainLocationGroupBox.setTitle(self.trUtf8('Display Location'))
|
||||
self.DefaultLocationLabel.setText(self.trUtf8('Use Default Location:'))
|
||||
self.FontMainXLabel.setText(self.trUtf8('X Position:'))
|
||||
self.FontMainYLabel.setText(self.trUtf8('Y Position:'))
|
||||
self.FontMainWidthLabel.setText(self.trUtf8('Width:'))
|
||||
self.FontMainHeightLabel.setText(self.trUtf8('Height:'))
|
||||
self.FontMainXSpinBox.setSuffix(self.trUtf8('px'))
|
||||
self.FontMainYSpinBox.setSuffix(self.trUtf8('px'))
|
||||
self.FontMainWidthSpinBox.setSuffix(self.trUtf8('px'))
|
||||
self.FontMainHeightSpinBox.setSuffix(self.trUtf8('px'))
|
||||
translate('AmendThemeForm', 'Background'))
|
||||
self.FontMainGroupBox.setTitle(translate('AmendThemeForm', 'Main Font'))
|
||||
self.FontMainlabel.setText(translate('AmendThemeForm', 'Font:'))
|
||||
self.FontMainColorLabel.setText(translate('AmendThemeForm', 'Font Color:'))
|
||||
self.FontMainSize.setText(translate('AmendThemeForm', 'Size:'))
|
||||
self.FontMainSizeSpinBox.setSuffix(translate('AmendThemeForm', 'pt'))
|
||||
self.FontMainWrapIndentationLabel.setText(translate('AmendThemeForm', 'Wrap Indentation'))
|
||||
self.FontMainWrapLineAdjustmentLabel.setText(translate('AmendThemeForm', 'Adjust Line Spacing'))
|
||||
self.FontMainWeightComboBox.setItemText(0, translate('AmendThemeForm', 'Normal'))
|
||||
self.FontMainWeightComboBox.setItemText(1, translate('AmendThemeForm', 'Bold'))
|
||||
self.FontMainWeightComboBox.setItemText(2, translate('AmendThemeForm', 'Italics'))
|
||||
self.FontMainWeightComboBox.setItemText(3, translate('AmendThemeForm', 'Bold/Italics'))
|
||||
self.FontMainWeightLabel.setText(translate('AmendThemeForm', 'Font Weight:'))
|
||||
self.MainLocationGroupBox.setTitle(translate('AmendThemeForm', 'Display Location'))
|
||||
self.DefaultLocationLabel.setText(translate('AmendThemeForm', 'Use Default Location:'))
|
||||
self.FontMainXLabel.setText(translate('AmendThemeForm', 'X Position:'))
|
||||
self.FontMainYLabel.setText(translate('AmendThemeForm', 'Y Position:'))
|
||||
self.FontMainWidthLabel.setText(translate('AmendThemeForm', 'Width:'))
|
||||
self.FontMainHeightLabel.setText(translate('AmendThemeForm', 'Height:'))
|
||||
self.FontMainXSpinBox.setSuffix(translate('AmendThemeForm', 'px'))
|
||||
self.FontMainYSpinBox.setSuffix(translate('AmendThemeForm', 'px'))
|
||||
self.FontMainWidthSpinBox.setSuffix(translate('AmendThemeForm', 'px'))
|
||||
self.FontMainHeightSpinBox.setSuffix(translate('AmendThemeForm', 'px'))
|
||||
self.ThemeTabWidget.setTabText(
|
||||
self.ThemeTabWidget.indexOf(self.FontMainTab),
|
||||
self.trUtf8('Font Main'))
|
||||
self.FooterFontGroupBox.setTitle(self.trUtf8('Footer Font'))
|
||||
self.FontFooterLabel.setText(self.trUtf8('Font:'))
|
||||
self.FontFooterColorLabel.setText(self.trUtf8('Font Color:'))
|
||||
self.FontFooterSizeLabel.setText(self.trUtf8('Size:'))
|
||||
self.FontFooterSizeSpinBox.setSuffix(self.trUtf8('pt'))
|
||||
self.FontFooterWeightComboBox.setItemText(0, self.trUtf8('Normal'))
|
||||
self.FontFooterWeightComboBox.setItemText(1, self.trUtf8('Bold'))
|
||||
self.FontFooterWeightComboBox.setItemText(2, self.trUtf8('Italics'))
|
||||
self.FontFooterWeightComboBox.setItemText(3, self.trUtf8('Bold/Italics'))
|
||||
self.FontFooterWeightLabel.setText(self.trUtf8('Font Weight:'))
|
||||
self.LocationFooterGroupBox.setTitle(self.trUtf8('Display Location'))
|
||||
self.FontFooterDefaultLabel.setText(self.trUtf8('Use Default Location:'))
|
||||
self.FontFooterXLabel.setText(self.trUtf8('X Position:'))
|
||||
self.FontFooterYLabel.setText(self.trUtf8('Y Position:'))
|
||||
self.FontFooterWidthLabel.setText(self.trUtf8('Width:'))
|
||||
self.FontFooterHeightLabel.setText(self.trUtf8('Height:'))
|
||||
self.FontFooterXSpinBox.setSuffix(self.trUtf8('px'))
|
||||
self.FontFooterYSpinBox.setSuffix(self.trUtf8('px'))
|
||||
self.FontFooterWidthSpinBox.setSuffix(self.trUtf8('px'))
|
||||
self.FontFooterHeightSpinBox.setSuffix(self.trUtf8('px'))
|
||||
translate('AmendThemeForm', 'Font Main'))
|
||||
self.FooterFontGroupBox.setTitle(translate('AmendThemeForm', 'Footer Font'))
|
||||
self.FontFooterLabel.setText(translate('AmendThemeForm', 'Font:'))
|
||||
self.FontFooterColorLabel.setText(translate('AmendThemeForm', 'Font Color:'))
|
||||
self.FontFooterSizeLabel.setText(translate('AmendThemeForm', 'Size:'))
|
||||
self.FontFooterSizeSpinBox.setSuffix(translate('AmendThemeForm', 'pt'))
|
||||
self.FontFooterWeightComboBox.setItemText(0, translate('AmendThemeForm', 'Normal'))
|
||||
self.FontFooterWeightComboBox.setItemText(1, translate('AmendThemeForm', 'Bold'))
|
||||
self.FontFooterWeightComboBox.setItemText(2, translate('AmendThemeForm', 'Italics'))
|
||||
self.FontFooterWeightComboBox.setItemText(3, translate('AmendThemeForm', 'Bold/Italics'))
|
||||
self.FontFooterWeightLabel.setText(translate('AmendThemeForm', 'Font Weight:'))
|
||||
self.LocationFooterGroupBox.setTitle(translate('AmendThemeForm', 'Display Location'))
|
||||
self.FontFooterDefaultLabel.setText(translate('AmendThemeForm', 'Use Default Location:'))
|
||||
self.FontFooterXLabel.setText(translate('AmendThemeForm', 'X Position:'))
|
||||
self.FontFooterYLabel.setText(translate('AmendThemeForm', 'Y Position:'))
|
||||
self.FontFooterWidthLabel.setText(translate('AmendThemeForm', 'Width:'))
|
||||
self.FontFooterHeightLabel.setText(translate('AmendThemeForm', 'Height:'))
|
||||
self.FontFooterXSpinBox.setSuffix(translate('AmendThemeForm', 'px'))
|
||||
self.FontFooterYSpinBox.setSuffix(translate('AmendThemeForm', 'px'))
|
||||
self.FontFooterWidthSpinBox.setSuffix(translate('AmendThemeForm', 'px'))
|
||||
self.FontFooterHeightSpinBox.setSuffix(translate('AmendThemeForm', 'px'))
|
||||
self.ThemeTabWidget.setTabText(
|
||||
self.ThemeTabWidget.indexOf(self.FontFooterTab),
|
||||
self.trUtf8('Font Footer'))
|
||||
self.OutlineGroupBox.setTitle(self.trUtf8('Outline'))
|
||||
self.OutlineSpinBoxLabel.setText(self.trUtf8('Outline Size:'))
|
||||
self.OutlineSpinBox.setSuffix(self.trUtf8('px'))
|
||||
self.OutlineColorLabel.setText(self.trUtf8('Outline Color:'))
|
||||
self.OutlineEnabledLabel.setText(self.trUtf8('Show Outline:'))
|
||||
self.ShadowGroupBox.setTitle(self.trUtf8('Shadow'))
|
||||
self.ShadowSpinBoxLabel.setText(self.trUtf8('Shadow Size:'))
|
||||
self.ShadowSpinBox.setSuffix(self.trUtf8('px'))
|
||||
self.ShadowColorLabel.setText(self.trUtf8('Shadow Color:'))
|
||||
self.ShadowEnabledLabel.setText(self.trUtf8('Show Shadow:'))
|
||||
self.AlignmentGroupBox.setTitle(self.trUtf8('Alignment'))
|
||||
self.HorizontalLabel.setText(self.trUtf8('Horizontal Align:'))
|
||||
self.HorizontalComboBox.setItemText(0, self.trUtf8('Left'))
|
||||
self.HorizontalComboBox.setItemText(1, self.trUtf8('Right'))
|
||||
self.HorizontalComboBox.setItemText(2, self.trUtf8('Center'))
|
||||
self.VerticalLabel.setText(self.trUtf8('Vertical Align:'))
|
||||
self.VerticalComboBox.setItemText(0, self.trUtf8('Top'))
|
||||
self.VerticalComboBox.setItemText(1, self.trUtf8('Middle'))
|
||||
self.VerticalComboBox.setItemText(2, self.trUtf8('Bottom'))
|
||||
self.TransitionGroupBox.setTitle(self.trUtf8('Slide Transition'))
|
||||
self.SlideTransitionCheckedBoxLabel.setText(self.trUtf8('Transition Active:'))
|
||||
translate('AmendThemeForm', 'Font Footer'))
|
||||
self.OutlineGroupBox.setTitle(translate('AmendThemeForm', 'Outline'))
|
||||
self.OutlineSpinBoxLabel.setText(translate('AmendThemeForm', 'Outline Size:'))
|
||||
self.OutlineSpinBox.setSuffix(translate('AmendThemeForm', 'px'))
|
||||
self.OutlineColorLabel.setText(translate('AmendThemeForm', 'Outline Color:'))
|
||||
self.OutlineEnabledLabel.setText(translate('AmendThemeForm', 'Show Outline:'))
|
||||
self.ShadowGroupBox.setTitle(translate('AmendThemeForm', 'Shadow'))
|
||||
self.ShadowSpinBoxLabel.setText(translate('AmendThemeForm', 'Shadow Size:'))
|
||||
self.ShadowSpinBox.setSuffix(translate('AmendThemeForm', 'px'))
|
||||
self.ShadowColorLabel.setText(translate('AmendThemeForm', 'Shadow Color:'))
|
||||
self.ShadowEnabledLabel.setText(translate('AmendThemeForm', 'Show Shadow:'))
|
||||
self.AlignmentGroupBox.setTitle(translate('AmendThemeForm', 'Alignment'))
|
||||
self.HorizontalLabel.setText(translate('AmendThemeForm', 'Horizontal Align:'))
|
||||
self.HorizontalComboBox.setItemText(0, translate('AmendThemeForm', 'Left'))
|
||||
self.HorizontalComboBox.setItemText(1, translate('AmendThemeForm', 'Right'))
|
||||
self.HorizontalComboBox.setItemText(2, translate('AmendThemeForm', 'Center'))
|
||||
self.VerticalLabel.setText(translate('AmendThemeForm', 'Vertical Align:'))
|
||||
self.VerticalComboBox.setItemText(0, translate('AmendThemeForm', 'Top'))
|
||||
self.VerticalComboBox.setItemText(1, translate('AmendThemeForm', 'Middle'))
|
||||
self.VerticalComboBox.setItemText(2, translate('AmendThemeForm', 'Bottom'))
|
||||
self.TransitionGroupBox.setTitle(translate('AmendThemeForm', 'Slide Transition'))
|
||||
self.SlideTransitionCheckedBoxLabel.setText(translate('AmendThemeForm', 'Transition Active:'))
|
||||
self.ThemeTabWidget.setTabText(
|
||||
self.ThemeTabWidget.indexOf(self.OtherOptionsTab),
|
||||
self.trUtf8('Other Options'))
|
||||
self.PreviewGroupBox.setTitle(self.trUtf8('Preview'))
|
||||
translate('AmendThemeForm', 'Other Options'))
|
||||
self.PreviewGroupBox.setTitle(translate('AmendThemeForm', 'Preview'))
|
||||
|
@ -101,6 +101,9 @@ class AmendThemeForm(QtGui.QDialog, Ui_AmendThemeDialog):
|
||||
QtCore.QObject.connect(self.FontMainHeightSpinBox,
|
||||
QtCore.SIGNAL(u'editingFinished()'),
|
||||
self.onFontMainHeightSpinBoxChanged)
|
||||
QtCore.QObject.connect(self.FontMainLineAdjustmentSpinBox,
|
||||
QtCore.SIGNAL(u'editingFinished()'),
|
||||
self.onFontMainLineAdjustmentSpinBoxChanged)
|
||||
QtCore.QObject.connect(self.FontMainLineSpacingSpinBox,
|
||||
QtCore.SIGNAL(u'editingFinished()'),
|
||||
self.onFontMainLineSpacingSpinBoxChanged)
|
||||
@ -130,7 +133,8 @@ class AmendThemeForm(QtGui.QDialog, Ui_AmendThemeDialog):
|
||||
QtCore.SIGNAL(u'editingFinished()'),
|
||||
self.onOutlineSpinBoxChanged)
|
||||
QtCore.QObject.connect(self.SlideTransitionCheckedBox,
|
||||
QtCore.SIGNAL(u'stateChanged(int)'), self.onSlideTransitionCheckedBoxChanged)
|
||||
QtCore.SIGNAL(u'stateChanged(int)'),
|
||||
self.onSlideTransitionCheckedBoxChanged)
|
||||
|
||||
def accept(self):
|
||||
new_theme = ThemeXML()
|
||||
@ -142,10 +146,10 @@ class AmendThemeForm(QtGui.QDialog, Ui_AmendThemeDialog):
|
||||
new_theme.add_background_transparent()
|
||||
else:
|
||||
if self.theme.background_type == u'solid':
|
||||
new_theme.add_background_solid( \
|
||||
new_theme.add_background_solid(
|
||||
unicode(self.theme.background_color))
|
||||
elif self.theme.background_type == u'gradient':
|
||||
new_theme.add_background_gradient( \
|
||||
new_theme.add_background_gradient(
|
||||
unicode(self.theme.background_startColor),
|
||||
unicode(self.theme.background_endColor),
|
||||
self.theme.background_direction)
|
||||
@ -155,7 +159,6 @@ class AmendThemeForm(QtGui.QDialog, Ui_AmendThemeDialog):
|
||||
new_theme.add_background_image(filename)
|
||||
save_to = os.path.join(self.path, theme_name, filename)
|
||||
save_from = self.theme.background_filename
|
||||
|
||||
new_theme.add_font(unicode(self.theme.font_main_name),
|
||||
unicode(self.theme.font_main_color),
|
||||
unicode(self.theme.font_main_proportion),
|
||||
@ -163,6 +166,7 @@ class AmendThemeForm(QtGui.QDialog, Ui_AmendThemeDialog):
|
||||
unicode(self.theme.font_main_weight),
|
||||
unicode(self.theme.font_main_italics),
|
||||
unicode(self.theme.font_main_indentation),
|
||||
unicode(self.theme.font_main_line_adjustment),
|
||||
unicode(self.theme.font_main_x),
|
||||
unicode(self.theme.font_main_y),
|
||||
unicode(self.theme.font_main_width),
|
||||
@ -173,11 +177,12 @@ class AmendThemeForm(QtGui.QDialog, Ui_AmendThemeDialog):
|
||||
unicode(self.theme.font_footer_override), u'footer',
|
||||
unicode(self.theme.font_footer_weight),
|
||||
unicode(self.theme.font_footer_italics),
|
||||
0,
|
||||
0, # indentation
|
||||
0, # line adjustment
|
||||
unicode(self.theme.font_footer_x),
|
||||
unicode(self.theme.font_footer_y),
|
||||
unicode(self.theme.font_footer_width),
|
||||
unicode(self.theme.font_footer_height) )
|
||||
unicode(self.theme.font_footer_height))
|
||||
new_theme.add_display(unicode(self.theme.display_shadow),
|
||||
unicode(self.theme.display_shadow_color),
|
||||
unicode(self.theme.display_outline),
|
||||
@ -261,6 +266,8 @@ class AmendThemeForm(QtGui.QDialog, Ui_AmendThemeDialog):
|
||||
self.FontMainYSpinBox.setValue(self.theme.font_main_y)
|
||||
self.FontMainWidthSpinBox.setValue(self.theme.font_main_width)
|
||||
self.FontMainHeightSpinBox.setValue(self.theme.font_main_height)
|
||||
self.FontMainLineAdjustmentSpinBox.setValue(
|
||||
self.theme.font_main_line_adjustment)
|
||||
self.FontMainLineSpacingSpinBox.setValue(
|
||||
self.theme.font_main_indentation)
|
||||
self.stateChanging(self.theme)
|
||||
@ -281,6 +288,13 @@ class AmendThemeForm(QtGui.QDialog, Ui_AmendThemeDialog):
|
||||
self.theme.font_main_width = self.FontMainWidthSpinBox.value()
|
||||
self.previewTheme()
|
||||
|
||||
def onFontMainLineAdjustmentSpinBoxChanged(self):
|
||||
if self.theme.font_main_line_adjustment != \
|
||||
self.FontMainLineAdjustmentSpinBox.value():
|
||||
self.theme.font_main_line_adjustment = \
|
||||
self.FontMainLineAdjustmentSpinBox.value()
|
||||
self.previewTheme()
|
||||
|
||||
def onFontMainLineSpacingSpinBoxChanged(self):
|
||||
if self.theme.font_main_indentation != \
|
||||
self.FontMainLineSpacingSpinBox.value():
|
||||
@ -687,7 +701,8 @@ class AmendThemeForm(QtGui.QDialog, Ui_AmendThemeDialog):
|
||||
if self.allowPreview:
|
||||
#calculate main number of rows
|
||||
metrics = self._getThemeMetrics()
|
||||
line_height = metrics.height()
|
||||
line_height = metrics.height() \
|
||||
+ int(self.theme.font_main_line_adjustment)
|
||||
if self.theme.display_shadow:
|
||||
line_height += int(self.theme.display_shadow_size)
|
||||
if self.theme.display_outline:
|
||||
@ -700,7 +715,6 @@ class AmendThemeForm(QtGui.QDialog, Ui_AmendThemeDialog):
|
||||
page_length))
|
||||
page_length_text = unicode(self.trUtf8('Slide Height is %s rows'))
|
||||
self.FontMainLinesPageLabel.setText(page_length_text % page_length)
|
||||
#a=c
|
||||
frame = self.thememanager.generateImage(self.theme)
|
||||
self.ThemePreview.setPixmap(QtGui.QPixmap.fromImage(frame))
|
||||
|
||||
|
235
openlp/core/ui/displaytab.py
Normal file
@ -0,0 +1,235 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
# vim: autoindent shiftwidth=4 expandtab textwidth=80 tabstop=4 softtabstop=4
|
||||
|
||||
###############################################################################
|
||||
# OpenLP - Open Source Lyrics Projection #
|
||||
# --------------------------------------------------------------------------- #
|
||||
# Copyright (c) 2008-2010 Raoul Snyman #
|
||||
# Portions copyright (c) 2008-2010 Tim Bentley, Jonathan Corwin, Michael #
|
||||
# Gorven, Scott Guerrieri, Christian Richter, Maikel Stuivenberg, Martin #
|
||||
# Thompson, Jon Tibble, Carsten Tinggaard #
|
||||
# --------------------------------------------------------------------------- #
|
||||
# This program is free software; you can redistribute it and/or modify it #
|
||||
# under the terms of the GNU General Public License as published by the Free #
|
||||
# Software Foundation; version 2 of the License. #
|
||||
# #
|
||||
# This program is distributed in the hope that it will be useful, but WITHOUT #
|
||||
# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or #
|
||||
# FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for #
|
||||
# more details. #
|
||||
# #
|
||||
# You should have received a copy of the GNU General Public License along #
|
||||
# with this program; if not, write to the Free Software Foundation, Inc., 59 #
|
||||
# Temple Place, Suite 330, Boston, MA 02111-1307 USA #
|
||||
###############################################################################
|
||||
|
||||
from PyQt4 import QtGui, QtCore
|
||||
|
||||
from openlp.core.lib import SettingsTab, Receiver
|
||||
|
||||
class DisplayTab(SettingsTab):
|
||||
"""
|
||||
Class documentation goes here.
|
||||
"""
|
||||
def __init__(self, screens):
|
||||
"""
|
||||
Constructor
|
||||
"""
|
||||
self.screens = screens
|
||||
SettingsTab.__init__(self, u'Display')
|
||||
|
||||
def setupUi(self):
|
||||
self.tabTitleVisible = self.trUtf8('Displays')
|
||||
self.layoutWidget = QtGui.QWidget(self)
|
||||
self.layoutWidget.setGeometry(QtCore.QRect(0, 40, 241, 79))
|
||||
self.layoutWidget.setObjectName(u'layoutWidget')
|
||||
self.verticalLayout = QtGui.QVBoxLayout(self.layoutWidget)
|
||||
self.verticalLayout.setObjectName(u'verticalLayout')
|
||||
self.CurrentGroupBox = QtGui.QGroupBox(self.layoutWidget)
|
||||
self.CurrentGroupBox.setObjectName(u'CurrentGroupBox')
|
||||
self.horizontalLayout = QtGui.QHBoxLayout(self.CurrentGroupBox)
|
||||
self.horizontalLayout.setObjectName(u'horizontalLayout')
|
||||
self.verticalLayout_6 = QtGui.QVBoxLayout()
|
||||
self.verticalLayout_6.setObjectName(u'verticalLayout_6')
|
||||
self.XLabel = QtGui.QLabel(self.CurrentGroupBox)
|
||||
self.XLabel.setAlignment(QtCore.Qt.AlignCenter)
|
||||
self.XLabel.setObjectName(u'XLabel')
|
||||
self.verticalLayout_6.addWidget(self.XLabel)
|
||||
self.Xpos = QtGui.QLabel(self.CurrentGroupBox)
|
||||
self.Xpos.setAlignment(QtCore.Qt.AlignCenter)
|
||||
self.Xpos.setObjectName(u'Xpos')
|
||||
self.verticalLayout_6.addWidget(self.Xpos)
|
||||
self.horizontalLayout.addLayout(self.verticalLayout_6)
|
||||
self.verticalLayout_7 = QtGui.QVBoxLayout()
|
||||
self.verticalLayout_7.setObjectName(u'verticalLayout_7')
|
||||
self.YLabel = QtGui.QLabel(self.CurrentGroupBox)
|
||||
self.YLabel.setAlignment(QtCore.Qt.AlignCenter)
|
||||
self.YLabel.setObjectName(u'YLabel')
|
||||
self.verticalLayout_7.addWidget(self.YLabel)
|
||||
self.Ypos = QtGui.QLabel(self.CurrentGroupBox)
|
||||
self.Ypos.setAlignment(QtCore.Qt.AlignCenter)
|
||||
self.Ypos.setObjectName(u'Ypos')
|
||||
self.verticalLayout_7.addWidget(self.Ypos)
|
||||
self.horizontalLayout.addLayout(self.verticalLayout_7)
|
||||
self.verticalLayout_9 = QtGui.QVBoxLayout()
|
||||
self.verticalLayout_9.setObjectName(u'verticalLayout_9')
|
||||
self.HeightLabel = QtGui.QLabel(self.CurrentGroupBox)
|
||||
self.HeightLabel.setMaximumSize(QtCore.QSize(100, 16777215))
|
||||
self.HeightLabel.setAlignment(QtCore.Qt.AlignCenter)
|
||||
self.HeightLabel.setObjectName(u'HeightLabel')
|
||||
self.verticalLayout_9.addWidget(self.HeightLabel)
|
||||
self.Height = QtGui.QLabel(self.CurrentGroupBox)
|
||||
self.Height.setAlignment(QtCore.Qt.AlignCenter)
|
||||
self.Height.setObjectName(u'Height')
|
||||
self.verticalLayout_9.addWidget(self.Height)
|
||||
self.horizontalLayout.addLayout(self.verticalLayout_9)
|
||||
self.verticalLayout_8 = QtGui.QVBoxLayout()
|
||||
self.verticalLayout_8.setObjectName(u'verticalLayout_8')
|
||||
self.WidthLabel = QtGui.QLabel(self.CurrentGroupBox)
|
||||
self.WidthLabel.setAlignment(QtCore.Qt.AlignCenter)
|
||||
self.WidthLabel.setObjectName(u'WidthLabel')
|
||||
self.verticalLayout_8.addWidget(self.WidthLabel)
|
||||
self.Width = QtGui.QLabel(self.CurrentGroupBox)
|
||||
self.Width.setAlignment(QtCore.Qt.AlignCenter)
|
||||
self.Width.setObjectName(u'Width')
|
||||
self.verticalLayout_8.addWidget(self.Width)
|
||||
self.horizontalLayout.addLayout(self.verticalLayout_8)
|
||||
self.verticalLayout.addWidget(self.CurrentGroupBox)
|
||||
self.CurrentGroupBox_2 = QtGui.QGroupBox(self)
|
||||
self.CurrentGroupBox_2.setGeometry(QtCore.QRect(0, 130, 248, 87))
|
||||
self.CurrentGroupBox_2.setMaximumSize(QtCore.QSize(500, 16777215))
|
||||
self.CurrentGroupBox_2.setObjectName(u'CurrentGroupBox_2')
|
||||
self.horizontalLayout_2 = QtGui.QHBoxLayout(self.CurrentGroupBox_2)
|
||||
self.horizontalLayout_2.setObjectName(u'horizontalLayout_2')
|
||||
self.verticalLayout_2 = QtGui.QVBoxLayout()
|
||||
self.verticalLayout_2.setObjectName(u'verticalLayout_2')
|
||||
self.XAmendLabel = QtGui.QLabel(self.CurrentGroupBox_2)
|
||||
self.XAmendLabel.setAlignment(QtCore.Qt.AlignCenter)
|
||||
self.XAmendLabel.setObjectName(u'XAmendLabel')
|
||||
self.verticalLayout_2.addWidget(self.XAmendLabel)
|
||||
self.XposEdit = QtGui.QLineEdit(self.CurrentGroupBox_2)
|
||||
self.XposEdit.setMaximumSize(QtCore.QSize(50, 16777215))
|
||||
self.XposEdit.setMaxLength(4)
|
||||
self.XposEdit.setObjectName(u'XposEdit')
|
||||
self.verticalLayout_2.addWidget(self.XposEdit)
|
||||
self.horizontalLayout_2.addLayout(self.verticalLayout_2)
|
||||
self.verticalLayout_3 = QtGui.QVBoxLayout()
|
||||
self.verticalLayout_3.setObjectName(u'verticalLayout_3')
|
||||
self.YAmendLabel = QtGui.QLabel(self.CurrentGroupBox_2)
|
||||
self.YAmendLabel.setAlignment(QtCore.Qt.AlignCenter)
|
||||
self.YAmendLabel.setObjectName(u'YAmendLabel')
|
||||
self.verticalLayout_3.addWidget(self.YAmendLabel)
|
||||
self.YposEdit = QtGui.QLineEdit(self.CurrentGroupBox_2)
|
||||
self.YposEdit.setMaximumSize(QtCore.QSize(50, 16777215))
|
||||
self.YposEdit.setMaxLength(4)
|
||||
self.YposEdit.setObjectName(u'YposEdit')
|
||||
self.verticalLayout_3.addWidget(self.YposEdit)
|
||||
self.horizontalLayout_2.addLayout(self.verticalLayout_3)
|
||||
self.verticalLayout_4 = QtGui.QVBoxLayout()
|
||||
self.verticalLayout_4.setObjectName(u'verticalLayout_4')
|
||||
self.HeightAmendLabel = QtGui.QLabel(self.CurrentGroupBox_2)
|
||||
self.HeightAmendLabel.setAlignment(QtCore.Qt.AlignCenter)
|
||||
self.HeightAmendLabel.setObjectName(u'HeightAmendLabel')
|
||||
self.verticalLayout_4.addWidget(self.HeightAmendLabel)
|
||||
self.HeightEdit = QtGui.QLineEdit(self.CurrentGroupBox_2)
|
||||
self.HeightEdit.setMaximumSize(QtCore.QSize(50, 16777215))
|
||||
self.HeightEdit.setMaxLength(4)
|
||||
self.HeightEdit.setObjectName(u'HeightEdit')
|
||||
self.verticalLayout_4.addWidget(self.HeightEdit)
|
||||
self.horizontalLayout_2.addLayout(self.verticalLayout_4)
|
||||
self.verticalLayout_5 = QtGui.QVBoxLayout()
|
||||
self.verticalLayout_5.setSizeConstraint(QtGui.QLayout.SetMinimumSize)
|
||||
self.verticalLayout_5.setObjectName(u'verticalLayout_5')
|
||||
self.WidthAmendLabel = QtGui.QLabel(self.CurrentGroupBox_2)
|
||||
self.WidthAmendLabel.setMaximumSize(QtCore.QSize(100, 16777215))
|
||||
self.WidthAmendLabel.setAlignment(QtCore.Qt.AlignCenter)
|
||||
self.WidthAmendLabel.setObjectName(u'WidthAmendLabel')
|
||||
self.verticalLayout_5.addWidget(self.WidthAmendLabel)
|
||||
self.WidthEdit = QtGui.QLineEdit(self.CurrentGroupBox_2)
|
||||
self.WidthEdit.setMaximumSize(QtCore.QSize(60, 16777215))
|
||||
self.WidthEdit.setObjectName(u'WidthEdit')
|
||||
self.verticalLayout_5.addWidget(self.WidthEdit)
|
||||
self.horizontalLayout_2.addLayout(self.verticalLayout_5)
|
||||
self.OverrideCheckBox = QtGui.QCheckBox(self)
|
||||
self.OverrideCheckBox.setGeometry(QtCore.QRect(0, 10, 191, 23))
|
||||
self.OverrideCheckBox.setObjectName(u'OverrideCheckBox')
|
||||
QtCore.QMetaObject.connectSlotsByName(self)
|
||||
QtCore.QObject.connect(self.OverrideCheckBox,
|
||||
QtCore.SIGNAL(u'stateChanged(int)'),
|
||||
self.onOverrideCheckBoxChanged)
|
||||
|
||||
def retranslateUi(self):
|
||||
self.setWindowTitle( self.trUtf8(u'Amend Display Settings'))
|
||||
self.CurrentGroupBox.setTitle( self.trUtf8(u'Default Settings'))
|
||||
self.XLabel.setText(self.trUtf8(u'X'))
|
||||
self.Xpos.setText(u'0')
|
||||
self.YLabel.setText( self.trUtf8(u'Y'))
|
||||
self.Ypos.setText(u'0')
|
||||
self.HeightLabel.setText( self.trUtf8(u'Height'))
|
||||
self.Height.setText(u'0')
|
||||
self.WidthLabel.setText( self.trUtf8(u'Width'))
|
||||
self.Width.setText(u'0')
|
||||
self.CurrentGroupBox_2.setTitle( self.trUtf8(u'Amend Settings'))
|
||||
self.XAmendLabel.setText( self.trUtf8(u'X'))
|
||||
self.YAmendLabel.setText( self.trUtf8(u'Y'))
|
||||
self.HeightAmendLabel.setText( self.trUtf8(u'Height'))
|
||||
self.WidthAmendLabel.setText( self.trUtf8(u'Width'))
|
||||
self.OverrideCheckBox.setText( self.trUtf8(u'Override Output Display'))
|
||||
|
||||
def load(self):
|
||||
settings = QtCore.QSettings()
|
||||
settings.beginGroup(self.settingsSection)
|
||||
self.Xpos.setText(unicode(self.screens.current[u'size'].x()))
|
||||
self.Ypos.setText(unicode(self.screens.current[u'size'].y()))
|
||||
self.Height.setText(unicode(self.screens.current[u'size'].height()))
|
||||
self.Width.setText(unicode(self.screens.current[u'size'].width()))
|
||||
xpos = settings.value(u'x position',
|
||||
QtCore.QVariant(self.screens.current[u'size'].x())).toString()
|
||||
self.XposEdit.setText(xpos)
|
||||
ypos = settings.value(u'y position',
|
||||
QtCore.QVariant(self.screens.current[u'size'].y())).toString()
|
||||
self.YposEdit.setText(ypos)
|
||||
height = settings.value(u'height',
|
||||
QtCore.QVariant(self.screens.current[u'size'].height())).toString()
|
||||
self.HeightEdit.setText(height)
|
||||
width = settings.value(u'width',
|
||||
QtCore.QVariant(self.screens.current[u'size'].width())).toString()
|
||||
self.WidthEdit.setText(width)
|
||||
self.amend_display = settings.value(u'amend display',
|
||||
QtCore.QVariant(False)).toBool()
|
||||
self.OverrideCheckBox.setChecked(self.amend_display)
|
||||
self.amend_display_start = self.amend_display
|
||||
|
||||
def onOverrideCheckBoxChanged(self, check_state):
|
||||
self.amend_display = False
|
||||
# we have a set value convert to True/False
|
||||
if check_state == QtCore.Qt.Checked:
|
||||
self.amend_display = True
|
||||
|
||||
def save(self):
|
||||
settings = QtCore.QSettings()
|
||||
settings.beginGroup(self.settingsSection)
|
||||
settings.setValue('x position',
|
||||
QtCore.QVariant(self.XposEdit.text()))
|
||||
settings.setValue('y position',
|
||||
QtCore.QVariant(self.YposEdit.text()))
|
||||
settings.setValue('height',
|
||||
QtCore.QVariant(self.HeightEdit.text()))
|
||||
settings.setValue('width',
|
||||
QtCore.QVariant(self.WidthEdit.text()))
|
||||
settings.setValue('amend display',
|
||||
QtCore.QVariant(self.amend_display))
|
||||
self.postSetUp()
|
||||
|
||||
def postSetUp(self):
|
||||
self.screens.override[u'size'] = QtCore.QRect(int(self.XposEdit.text()),\
|
||||
int(self.YposEdit.text()), int(self.WidthEdit.text()),\
|
||||
int(self.HeightEdit.text()))
|
||||
if self.amend_display:
|
||||
self.screens.set_override_display()
|
||||
else:
|
||||
self.screens.reset_current_display()
|
||||
#only trigger event if data has changed in this edit session
|
||||
if self.amend_display_start != self.amend_display:
|
||||
self.amend_display_start = self.amend_display
|
||||
Receiver.send_message(u'config_screen_changed')
|
@ -25,16 +25,33 @@
|
||||
|
||||
from PyQt4 import QtCore, QtGui
|
||||
|
||||
from openlp.core.lib import SettingsTab, str_to_bool
|
||||
from openlp.core.lib import SettingsTab, Receiver
|
||||
|
||||
class GeneralTab(SettingsTab):
|
||||
"""
|
||||
GeneralTab is the general settings tab in the settings dialog.
|
||||
"""
|
||||
def __init__(self, screen_list):
|
||||
self.screen_list = screen_list
|
||||
def __init__(self, screens):
|
||||
self.screens = screens
|
||||
SettingsTab.__init__(self, u'General')
|
||||
|
||||
def preLoad(self):
|
||||
"""
|
||||
Set up the display screen and set correct screen
|
||||
values.
|
||||
If not set before default to last screen.
|
||||
"""
|
||||
settings = QtCore.QSettings()
|
||||
settings.beginGroup(self.settingsSection)
|
||||
self.MonitorNumber = settings.value(u'monitor',
|
||||
QtCore.QVariant(self.screens.display_count - 1)).toInt()[0]
|
||||
self.screens.set_current_display(self.MonitorNumber)
|
||||
self.screens.monitor_number = self.MonitorNumber
|
||||
self.DisplayOnMonitor = settings.value(
|
||||
u'display on monitor', QtCore.QVariant(True)).toBool()
|
||||
self.screens.display = self.DisplayOnMonitor
|
||||
settings.endGroup()
|
||||
|
||||
def setupUi(self):
|
||||
self.setObjectName(u'GeneralTab')
|
||||
self.tabTitleVisible = self.trUtf8('General')
|
||||
@ -60,6 +77,10 @@ class GeneralTab(SettingsTab):
|
||||
self.MonitorComboBox = QtGui.QComboBox(self.MonitorGroupBox)
|
||||
self.MonitorComboBox.setObjectName(u'MonitorComboBox')
|
||||
self.MonitorLayout.addWidget(self.MonitorComboBox)
|
||||
self.MonitorLayout.addWidget(self.MonitorComboBox)
|
||||
self.DisplayOnMonitorCheck = QtGui.QCheckBox(self.MonitorGroupBox)
|
||||
self.DisplayOnMonitorCheck.setObjectName(u'MonitorComboBox')
|
||||
self.MonitorLayout.addWidget(self.DisplayOnMonitorCheck)
|
||||
self.GeneralLeftLayout.addWidget(self.MonitorGroupBox)
|
||||
self.StartupGroupBox = QtGui.QGroupBox(self.GeneralLeftWidget)
|
||||
self.StartupGroupBox.setObjectName(u'StartupGroupBox')
|
||||
@ -133,14 +154,19 @@ class GeneralTab(SettingsTab):
|
||||
self.GeneralLayout.addWidget(self.GeneralRightWidget)
|
||||
QtCore.QObject.connect(self.MonitorComboBox,
|
||||
QtCore.SIGNAL(u'activated(int)'), self.onMonitorComboBoxChanged)
|
||||
QtCore.QObject.connect(self.DisplayOnMonitorCheck,
|
||||
QtCore.SIGNAL(u'stateChanged(int)'),
|
||||
self.onDisplayOnMonitorCheckChanged)
|
||||
QtCore.QObject.connect(self.WarningCheckBox,
|
||||
QtCore.SIGNAL(u'stateChanged(int)'), self.onWarningCheckBoxChanged)
|
||||
QtCore.QObject.connect(self.AutoOpenCheckBox,
|
||||
QtCore.SIGNAL(u'stateChanged(int)'), self.onAutoOpenCheckBoxChanged)
|
||||
QtCore.QObject.connect(self.ShowSplashCheckBox,
|
||||
QtCore.SIGNAL(u'stateChanged(int)'), self.onShowSplashCheckBoxChanged)
|
||||
QtCore.SIGNAL(u'stateChanged(int)'),
|
||||
self.onShowSplashCheckBoxChanged)
|
||||
QtCore.QObject.connect(self.SaveCheckServiceCheckBox,
|
||||
QtCore.SIGNAL(u'stateChanged(int)'), self.onSaveCheckServiceCheckBox)
|
||||
QtCore.SIGNAL(u'stateChanged(int)'),
|
||||
self.onSaveCheckServiceCheckBox)
|
||||
QtCore.QObject.connect(self.AutoPreviewCheckBox,
|
||||
QtCore.SIGNAL(u'stateChanged(int)'), self.onAutoPreviewCheckBox)
|
||||
QtCore.QObject.connect(self.NumberEdit,
|
||||
@ -152,14 +178,20 @@ class GeneralTab(SettingsTab):
|
||||
|
||||
def retranslateUi(self):
|
||||
self.MonitorGroupBox.setTitle(self.trUtf8('Monitors'))
|
||||
self.MonitorLabel.setText(self.trUtf8('Select monitor for output display:'))
|
||||
self.MonitorLabel.setText(
|
||||
self.trUtf8('Select monitor for output display:'))
|
||||
self.DisplayOnMonitorCheck.setText(
|
||||
self.trUtf8('Display if a single screen'))
|
||||
self.StartupGroupBox.setTitle(self.trUtf8('Application Startup'))
|
||||
self.WarningCheckBox.setText(self.trUtf8('Show blank screen warning'))
|
||||
self.AutoOpenCheckBox.setText(self.trUtf8('Automatically open the last service'))
|
||||
self.AutoOpenCheckBox.setText(
|
||||
self.trUtf8('Automatically open the last service'))
|
||||
self.ShowSplashCheckBox.setText(self.trUtf8('Show the splash screen'))
|
||||
self.SettingsGroupBox.setTitle(self.trUtf8('Application Settings'))
|
||||
self.SaveCheckServiceCheckBox.setText(self.trUtf8('Prompt to save Service before starting New'))
|
||||
self.AutoPreviewCheckBox.setText(self.trUtf8('Preview Next Song from Service Manager'))
|
||||
self.SaveCheckServiceCheckBox.setText(
|
||||
self.trUtf8('Prompt to save Service before starting New'))
|
||||
self.AutoPreviewCheckBox.setText(
|
||||
self.trUtf8('Preview Next Song from Service Manager'))
|
||||
self.CCLIGroupBox.setTitle(self.trUtf8('CCLI Details'))
|
||||
self.NumberLabel.setText(self.trUtf8('CCLI Number:'))
|
||||
self.UsernameLabel.setText(self.trUtf8('SongSelect Username:'))
|
||||
@ -168,6 +200,9 @@ class GeneralTab(SettingsTab):
|
||||
def onMonitorComboBoxChanged(self):
|
||||
self.MonitorNumber = self.MonitorComboBox.currentIndex()
|
||||
|
||||
def onDisplayOnMonitorCheckChanged(self, value):
|
||||
self.DisplayOnMonitor = (value == QtCore.Qt.Checked)
|
||||
|
||||
def onAutoOpenCheckBoxChanged(self, value):
|
||||
self.AutoOpen = (value == QtCore.Qt.Checked)
|
||||
|
||||
@ -193,24 +228,36 @@ class GeneralTab(SettingsTab):
|
||||
self.Password = self.PasswordEdit.displayText()
|
||||
|
||||
def load(self):
|
||||
for screen in self.screen_list.screen_list:
|
||||
screen_name = u'%s %d' % (self.trUtf8('Screen'), screen[u'number'] + 1)
|
||||
settings = QtCore.QSettings()
|
||||
settings.beginGroup(self.settingsSection)
|
||||
for screen in self.screens.screen_list:
|
||||
screen_name = u'%s %d' % (self.trUtf8('Screen'),
|
||||
screen[u'number'] + 1)
|
||||
if screen[u'primary']:
|
||||
screen_name = u'%s (%s)' % (screen_name, self.trUtf8('primary'))
|
||||
self.MonitorComboBox.addItem(screen_name)
|
||||
# Get the configs
|
||||
self.MonitorNumber = int(self.config.get_config(u'monitor', u'0'))
|
||||
self.Warning = str_to_bool(self.config.get_config(u'blank warning', u'False'))
|
||||
self.AutoOpen = str_to_bool(self.config.get_config(u'auto open', u'False'))
|
||||
self.ShowSplash = str_to_bool(self.config.get_config(u'show splash', u'True'))
|
||||
self.PromptSaveService = str_to_bool(self.config.get_config(u'save prompt', u'False'))
|
||||
self.AutoPreview = str_to_bool(self.config.get_config(u'auto preview', u'False'))
|
||||
self.CCLINumber = unicode(self.config.get_config(u'ccli number', u''))
|
||||
self.Username = unicode(self.config.get_config(u'songselect username', u''))
|
||||
self.Password = unicode(self.config.get_config(u'songselect password', u''))
|
||||
self.Warning = settings.value(
|
||||
u'blank warning', QtCore.QVariant(False)).toBool()
|
||||
self.AutoOpen = settings.value(
|
||||
u'auto open', QtCore.QVariant(False)).toBool()
|
||||
self.ShowSplash = settings.value(
|
||||
u'show splash', QtCore.QVariant(True)).toBool()
|
||||
self.PromptSaveService = settings.value(
|
||||
u'save prompt', QtCore.QVariant(False)).toBool()
|
||||
self.AutoPreview = settings.value(
|
||||
u'auto preview', QtCore.QVariant(False)).toBool()
|
||||
self.CCLINumber = unicode(settings.value(
|
||||
u'ccli number', QtCore.QVariant(u'')).toString())
|
||||
self.Username = unicode(settings.value(
|
||||
u'songselect username', QtCore.QVariant(u'')).toString())
|
||||
self.Password = unicode(settings.value(
|
||||
u'songselect password', QtCore.QVariant(u'')).toString())
|
||||
settings.endGroup()
|
||||
self.SaveCheckServiceCheckBox.setChecked(self.PromptSaveService)
|
||||
# Set a few things up
|
||||
self.MonitorComboBox.setCurrentIndex(self.MonitorNumber)
|
||||
self.DisplayOnMonitorCheck.setChecked(self.DisplayOnMonitor)
|
||||
self.WarningCheckBox.setChecked(self.Warning)
|
||||
self.AutoOpenCheckBox.setChecked(self.AutoOpen)
|
||||
self.ShowSplashCheckBox.setChecked(self.ShowSplash)
|
||||
@ -220,12 +267,27 @@ class GeneralTab(SettingsTab):
|
||||
self.PasswordEdit.setText(self.Password)
|
||||
|
||||
def save(self):
|
||||
self.config.set_config(u'monitor', self.MonitorNumber)
|
||||
self.config.set_config(u'blank warning', self.Warning)
|
||||
self.config.set_config(u'auto open', self.AutoOpen)
|
||||
self.config.set_config(u'show splash', self.ShowSplash)
|
||||
self.config.set_config(u'save prompt', self.PromptSaveService)
|
||||
self.config.set_config(u'auto preview', self.AutoPreview)
|
||||
self.config.set_config(u'ccli number', self.CCLINumber)
|
||||
self.config.set_config(u'songselect username', self.Username)
|
||||
self.config.set_config(u'songselect password', self.Password)
|
||||
settings = QtCore.QSettings()
|
||||
settings.beginGroup(self.settingsSection)
|
||||
settings.setValue(u'monitor', QtCore.QVariant(self.MonitorNumber))
|
||||
settings.setValue(u'display on monitor',
|
||||
QtCore.QVariant(self.DisplayOnMonitor))
|
||||
settings.setValue(u'blank warning', QtCore.QVariant(self.Warning))
|
||||
settings.setValue(u'auto open', QtCore.QVariant(self.AutoOpen))
|
||||
settings.setValue(u'show splash', QtCore.QVariant(self.ShowSplash))
|
||||
settings.setValue(u'save prompt',
|
||||
QtCore.QVariant(self.PromptSaveService))
|
||||
settings.setValue(u'auto preview', QtCore.QVariant(self.AutoPreview))
|
||||
settings.setValue(u'ccli number', QtCore.QVariant(self.CCLINumber))
|
||||
settings.setValue(u'songselect username',
|
||||
QtCore.QVariant(self.Username))
|
||||
settings.setValue(u'songselect password',
|
||||
QtCore.QVariant(self.Password))
|
||||
settings.endGroup()
|
||||
self.screens.display = self.DisplayOnMonitor
|
||||
#Monitor Number has changed.
|
||||
if self.screens.monitor_number != self.MonitorNumber:
|
||||
self.screens.monitor_number = self.MonitorNumber
|
||||
self.screens.set_current_display(self.MonitorNumber)
|
||||
Receiver.send_message(u'config_screen_changed')
|
||||
Receiver.send_message(u'config_updated')
|
||||
|
@ -34,6 +34,28 @@ from openlp.core.ui import HideMode
|
||||
|
||||
log = logging.getLogger(__name__)
|
||||
|
||||
class DisplayManager(QtGui.QWidget):
|
||||
"""
|
||||
Wrapper class to hold the display widgets.
|
||||
I will provide API's in future to access the screens allow for
|
||||
extra displays to be added.
|
||||
RenderManager is poked in by MainWindow
|
||||
"""
|
||||
def __init__(self, screens):
|
||||
QtGui.QWidget.__init__(self)
|
||||
self.screens = screens
|
||||
self.videoDisplay = VideoDisplay(self, screens)
|
||||
self.mainDisplay = MainDisplay(self, screens)
|
||||
|
||||
def setup(self):
|
||||
self.videoDisplay.setup()
|
||||
self.mainDisplay.setup()
|
||||
|
||||
def close(self):
|
||||
self.videoDisplay.close()
|
||||
self.mainDisplay.close()
|
||||
|
||||
|
||||
class DisplayWidget(QtGui.QWidget):
|
||||
"""
|
||||
Customised version of QTableWidget which can respond to keyboard
|
||||
@ -42,28 +64,29 @@ class DisplayWidget(QtGui.QWidget):
|
||||
log.info(u'MainDisplay loaded')
|
||||
|
||||
def __init__(self, parent=None, name=None):
|
||||
QtGui.QWidget.__init__(self, parent)
|
||||
QtGui.QWidget.__init__(self, None)
|
||||
self.parent = parent
|
||||
self.hotkey_map = {QtCore.Qt.Key_Return: 'servicemanager_next_item',
|
||||
QtCore.Qt.Key_Space: 'live_slidecontroller_next_noloop',
|
||||
QtCore.Qt.Key_Enter: 'live_slidecontroller_next_noloop',
|
||||
QtCore.Qt.Key_0: 'servicemanager_next_item',
|
||||
QtCore.Qt.Key_Backspace: 'live_slidecontroller_previous_noloop'}
|
||||
self.hotkey_map = {
|
||||
QtCore.Qt.Key_Return: 'servicemanager_next_item',
|
||||
QtCore.Qt.Key_Space: 'slidecontroller_live_next_noloop',
|
||||
QtCore.Qt.Key_Enter: 'slidecontroller_live_next_noloop',
|
||||
QtCore.Qt.Key_0: 'servicemanager_next_item',
|
||||
QtCore.Qt.Key_Backspace: 'slidecontroller_live_previous_noloop'}
|
||||
|
||||
def keyPressEvent(self, event):
|
||||
if type(event) == QtGui.QKeyEvent:
|
||||
#here accept the event and do something
|
||||
if event.key() == QtCore.Qt.Key_Up:
|
||||
Receiver.send_message(u'live_slidecontroller_previous')
|
||||
Receiver.send_message(u'slidecontroller_live_previous')
|
||||
event.accept()
|
||||
elif event.key() == QtCore.Qt.Key_Down:
|
||||
Receiver.send_message(u'live_slidecontroller_next')
|
||||
Receiver.send_message(u'slidecontroller_live_next')
|
||||
event.accept()
|
||||
elif event.key() == QtCore.Qt.Key_PageUp:
|
||||
Receiver.send_message(u'live_slidecontroller_first')
|
||||
Receiver.send_message(u'slidecontroller_live_first')
|
||||
event.accept()
|
||||
elif event.key() == QtCore.Qt.Key_PageDown:
|
||||
Receiver.send_message(u'live_slidecontroller_last')
|
||||
Receiver.send_message(u'slidecontroller_live_last')
|
||||
event.accept()
|
||||
elif event.key() in self.hotkey_map:
|
||||
Receiver.send_message(self.hotkey_map[event.key()])
|
||||
@ -91,17 +114,18 @@ class MainDisplay(DisplayWidget):
|
||||
``screens``
|
||||
The list of screens.
|
||||
"""
|
||||
log.debug(u'Initilisation started')
|
||||
DisplayWidget.__init__(self, None)
|
||||
log.debug(u'Initialisation started')
|
||||
DisplayWidget.__init__(self, parent)
|
||||
self.setWindowFlags(QtCore.Qt.Window | QtCore.Qt.FramelessWindowHint)
|
||||
self.setWindowState(QtCore.Qt.WindowFullScreen)
|
||||
self.parent = parent
|
||||
self.setWindowTitle(u'OpenLP Display')
|
||||
# WA_TranslucentBackground is not available in QT4.4
|
||||
try:
|
||||
self.setAttribute(QtCore.Qt.WA_TranslucentBackground)
|
||||
except AttributeError:
|
||||
pass
|
||||
self.screens = screens
|
||||
self.mediaObject = Phonon.MediaObject(self)
|
||||
self.video = Phonon.VideoWidget()
|
||||
self.video.setVisible(False)
|
||||
self.audio = Phonon.AudioOutput(Phonon.VideoCategory, self.mediaObject)
|
||||
Phonon.createPath(self.mediaObject, self.video)
|
||||
Phonon.createPath(self.mediaObject, self.audio)
|
||||
self.display_image = QtGui.QLabel(self)
|
||||
self.display_image.setScaledContents(True)
|
||||
self.display_text = QtGui.QLabel(self)
|
||||
@ -112,41 +136,30 @@ class MainDisplay(DisplayWidget):
|
||||
self.displayBlank = False
|
||||
self.blankFrame = None
|
||||
self.frame = None
|
||||
self.firstTime = True
|
||||
self.mediaLoaded = False
|
||||
self.hasTransition = False
|
||||
self.mediaBackground = False
|
||||
QtCore.QObject.connect(Receiver.get_receiver(),
|
||||
QtCore.SIGNAL(u'live_slide_hide'), self.hideDisplay)
|
||||
QtCore.SIGNAL(u'videodisplay_start'), self.hideDisplayForVideo)
|
||||
QtCore.QObject.connect(Receiver.get_receiver(),
|
||||
QtCore.SIGNAL(u'live_slide_show'), self.showDisplay)
|
||||
QtCore.QObject.connect(self.mediaObject,
|
||||
QtCore.SIGNAL(u'finished()'), self.onMediaFinish)
|
||||
QtCore.SIGNAL(u'maindisplay_hide'), self.hideDisplay)
|
||||
QtCore.QObject.connect(Receiver.get_receiver(),
|
||||
QtCore.SIGNAL(u'media_start'), self.onMediaQueue)
|
||||
QtCore.SIGNAL(u'maindisplay_show'), self.showDisplay)
|
||||
QtCore.QObject.connect(Receiver.get_receiver(),
|
||||
QtCore.SIGNAL(u'media_play'), self.onMediaPlay)
|
||||
QtCore.QObject.connect(Receiver.get_receiver(),
|
||||
QtCore.SIGNAL(u'media_pause'), self.onMediaPause)
|
||||
QtCore.QObject.connect(Receiver.get_receiver(),
|
||||
QtCore.SIGNAL(u'media_stop'), self.onMediaStop)
|
||||
QtCore.SIGNAL(u'videodisplay_background'), self.hideDisplayForVideo)
|
||||
|
||||
def setup(self, screenNumber):
|
||||
def setup(self):
|
||||
"""
|
||||
Sets up the screen on a particular screen.
|
||||
@param (integer) screen This is the screen number.
|
||||
"""
|
||||
log.debug(u'Setup %s for %s ' %(self.screens, screenNumber))
|
||||
log.debug(u'Setup %s for %s ' % (
|
||||
self.screens, self.screens.monitor_number))
|
||||
self.setVisible(False)
|
||||
self.screen = self.screens.current
|
||||
#Sort out screen locations and sizes
|
||||
self.setGeometry(self.screen[u'size'])
|
||||
self.display_alert.setGeometry(self.screen[u'size'])
|
||||
self.video.setGeometry(self.screen[u'size'])
|
||||
self.display_image.resize(self.screen[u'size'].width(),
|
||||
self.screen[u'size'].height())
|
||||
self.display_text.resize(self.screen[u'size'].width(),
|
||||
self.screen[u'size'].height())
|
||||
self.display_image.resize(
|
||||
self.screen[u'size'].width(), self.screen[u'size'].height())
|
||||
self.display_text.resize(
|
||||
self.screen[u'size'].width(), self.screen[u'size'].height())
|
||||
self.setGeometry(self.screen[u'size'])
|
||||
#Build a custom splash screen
|
||||
self.InitialFrame = QtGui.QImage(
|
||||
self.screen[u'size'].width(),
|
||||
@ -171,10 +184,11 @@ class MainDisplay(DisplayWidget):
|
||||
painter.begin(self.blankFrame)
|
||||
painter.fillRect(self.blankFrame.rect(), QtCore.Qt.black)
|
||||
#build a blank transparent image
|
||||
self.transparent = QtGui.QPixmap(self.screen[u'size'].width(),
|
||||
self.screen[u'size'].height())
|
||||
self.transparent = QtGui.QPixmap(
|
||||
self.screen[u'size'].width(), self.screen[u'size'].height())
|
||||
self.transparent.fill(QtCore.Qt.transparent)
|
||||
self.display_alert.setPixmap(self.transparent)
|
||||
self.display_text.setPixmap(self.transparent)
|
||||
self.frameView(self.transparent)
|
||||
# To display or not to display?
|
||||
if not self.screen[u'primary']:
|
||||
@ -183,42 +197,88 @@ class MainDisplay(DisplayWidget):
|
||||
else:
|
||||
self.setVisible(False)
|
||||
self.primary = True
|
||||
Receiver.send_message(u'screen_changed')
|
||||
|
||||
def resetDisplay(self):
|
||||
Receiver.send_message(u'stop_display_loop')
|
||||
log.debug(u'resetDisplay')
|
||||
Receiver.send_message(u'slidecontroller_live_stop_loop')
|
||||
if self.primary:
|
||||
self.setVisible(False)
|
||||
else:
|
||||
self.showFullScreen()
|
||||
|
||||
def hideDisplay(self):
|
||||
self.mediaLoaded = True
|
||||
self.setVisible(False)
|
||||
def hideDisplayForVideo(self):
|
||||
"""
|
||||
Hides the main display if for the video to be played
|
||||
"""
|
||||
self.hideDisplay(HideMode.Screen)
|
||||
|
||||
def hideDisplay(self, mode=HideMode.Screen):
|
||||
"""
|
||||
Hide the display by making all layers transparent
|
||||
Store the images so they can be replaced when required
|
||||
"""
|
||||
log.debug(u'hideDisplay mode = %d', mode)
|
||||
self.storeImage = QtGui.QPixmap(self.display_image.pixmap())
|
||||
self.storeText = QtGui.QPixmap(self.display_text.pixmap())
|
||||
self.display_alert.setPixmap(self.transparent)
|
||||
self.display_text.setPixmap(self.transparent)
|
||||
if mode == HideMode.Screen:
|
||||
self.display_image.setPixmap(self.transparent)
|
||||
elif mode == HideMode.Blank:
|
||||
self.display_image.setPixmap(
|
||||
QtGui.QPixmap.fromImage(self.blankFrame))
|
||||
else:
|
||||
if self.parent.renderManager.renderer.bg_frame:
|
||||
self.display_image.setPixmap(QtGui.QPixmap.fromImage(
|
||||
self.parent.renderManager.renderer.bg_frame))
|
||||
else:
|
||||
self.display_image.setPixmap(
|
||||
QtGui.QPixmap.fromImage(self.blankFrame))
|
||||
self.moveToTop()
|
||||
|
||||
def moveToTop(self):
|
||||
log.debug(u'moveToTop')
|
||||
self.setWindowFlags(QtCore.Qt.WindowStaysOnTopHint |
|
||||
QtCore.Qt.FramelessWindowHint | QtCore.Qt.Dialog)
|
||||
self.show()
|
||||
|
||||
def showDisplay(self):
|
||||
self.mediaLoaded = False
|
||||
if not self.primary:
|
||||
self.setVisible(True)
|
||||
self.showFullScreen()
|
||||
Receiver.send_message(u'flush_alert')
|
||||
"""
|
||||
Show the stored layers so the screen reappears as it was
|
||||
originally.
|
||||
Make the stored images None to release memory.
|
||||
"""
|
||||
log.debug(u'showDisplay')
|
||||
if self.storeImage:
|
||||
self.display_image.setPixmap(self.storeImage)
|
||||
self.display_alert.setPixmap(self.transparent)
|
||||
if self.storeText:
|
||||
self.display_text.setPixmap(self.storeText)
|
||||
self.storeImage = None
|
||||
self.store = None
|
||||
self.moveToTop()
|
||||
Receiver.send_message(u'maindisplay_active')
|
||||
|
||||
def addImageWithText(self, frame):
|
||||
frame = resize_image(frame,
|
||||
self.screen[u'size'].width(),
|
||||
self.screen[u'size'].height() )
|
||||
log.debug(u'addImageWithText')
|
||||
frame = resize_image(
|
||||
frame, self.screen[u'size'].width(), self.screen[u'size'].height())
|
||||
self.display_image.setPixmap(QtGui.QPixmap.fromImage(frame))
|
||||
self.moveToTop()
|
||||
|
||||
def setAlertSize(self, top, height):
|
||||
log.debug(u'setAlertSize')
|
||||
self.display_alert.setGeometry(
|
||||
QtCore.QRect(0, top,
|
||||
self.screen[u'size'].width(), height))
|
||||
|
||||
def addAlertImage(self, frame, blank=False):
|
||||
log.debug(u'addAlertImage')
|
||||
if blank:
|
||||
self.display_alert.setPixmap(self.transparent)
|
||||
else:
|
||||
self.display_alert.setPixmap(frame)
|
||||
self.moveToTop()
|
||||
|
||||
def frameView(self, frame, transition=False):
|
||||
"""
|
||||
@ -231,14 +291,17 @@ class MainDisplay(DisplayWidget):
|
||||
if not self.displayBlank:
|
||||
if transition:
|
||||
if self.frame is not None:
|
||||
self.display_text.setPixmap(QtGui.QPixmap.fromImage(self.frame))
|
||||
self.display_text.setPixmap(
|
||||
QtGui.QPixmap.fromImage(self.frame))
|
||||
self.repaint()
|
||||
self.frame = None
|
||||
if frame[u'trans'] is not None:
|
||||
self.display_text.setPixmap(QtGui.QPixmap.fromImage(frame[u'trans']))
|
||||
self.display_text.setPixmap(
|
||||
QtGui.QPixmap.fromImage(frame[u'trans']))
|
||||
self.repaint()
|
||||
self.frame = frame[u'trans']
|
||||
self.display_text.setPixmap(QtGui.QPixmap.fromImage(frame[u'main']))
|
||||
self.display_text.setPixmap(
|
||||
QtGui.QPixmap.fromImage(frame[u'main']))
|
||||
self.display_frame = frame[u'main']
|
||||
self.repaint()
|
||||
else:
|
||||
@ -247,77 +310,179 @@ class MainDisplay(DisplayWidget):
|
||||
else:
|
||||
self.display_text.setPixmap(QtGui.QPixmap.fromImage(frame))
|
||||
self.display_frame = frame
|
||||
if not self.isVisible():
|
||||
if not self.isVisible() and self.screens.display:
|
||||
self.setVisible(True)
|
||||
self.showFullScreen()
|
||||
else:
|
||||
self.waitingFrame = frame
|
||||
self.waitingFrameTrans = transition
|
||||
|
||||
def blankDisplay(self, blankType=HideMode.Blank, blanked=True):
|
||||
log.debug(u'Blank main Display %d' % blanked)
|
||||
if blanked:
|
||||
self.displayBlank = True
|
||||
if blankType == HideMode.Blank:
|
||||
self.display_text.setPixmap(QtGui.QPixmap.fromImage(self.blankFrame))
|
||||
elif blankType == HideMode.Theme:
|
||||
theme = self.parent.RenderManager.renderer.bg_frame
|
||||
if not theme:
|
||||
theme = self.blankFrame
|
||||
self.display_text.setPixmap(QtGui.QPixmap.fromImage(theme))
|
||||
self.waitingFrame = None
|
||||
self.waitingFrameTrans = False
|
||||
class VideoDisplay(Phonon.VideoWidget):
|
||||
"""
|
||||
This is the form that is used to display videos on the projector.
|
||||
"""
|
||||
log.info(u'VideoDisplay Loaded')
|
||||
|
||||
def __init__(self, parent, screens,
|
||||
aspect=Phonon.VideoWidget.AspectRatioWidget):
|
||||
"""
|
||||
The constructor for the display form.
|
||||
|
||||
``parent``
|
||||
The parent widget.
|
||||
|
||||
``screens``
|
||||
The list of screens.
|
||||
"""
|
||||
log.debug(u'VideoDisplay Initialisation started')
|
||||
Phonon.VideoWidget.__init__(self)
|
||||
self.setWindowTitle(u'OpenLP Video Display')
|
||||
self.parent = parent
|
||||
self.screens = screens
|
||||
self.hidden = False
|
||||
self.message = None
|
||||
self.mediaObject = Phonon.MediaObject()
|
||||
self.setAspectRatio(aspect)
|
||||
self.audioObject = Phonon.AudioOutput(Phonon.VideoCategory)
|
||||
Phonon.createPath(self.mediaObject, self)
|
||||
Phonon.createPath(self.mediaObject, self.audioObject)
|
||||
flags = QtCore.Qt.FramelessWindowHint | QtCore.Qt.Dialog
|
||||
# WindowsStaysOnBottomHint is not available in QT4.4
|
||||
try:
|
||||
flags = flags | QtCore.Qt.WindowStaysOnBottomHint
|
||||
except AttributeError:
|
||||
pass
|
||||
self.setWindowFlags(flags)
|
||||
|
||||
QtCore.QObject.connect(Receiver.get_receiver(),
|
||||
QtCore.SIGNAL(u'maindisplay_hide'), self.mediaHide)
|
||||
QtCore.QObject.connect(Receiver.get_receiver(),
|
||||
QtCore.SIGNAL(u'maindisplay_show'), self.mediaShow)
|
||||
QtCore.QObject.connect(Receiver.get_receiver(),
|
||||
QtCore.SIGNAL(u'videodisplay_start'), self.onMediaQueue)
|
||||
QtCore.QObject.connect(Receiver.get_receiver(),
|
||||
QtCore.SIGNAL(u'videodisplay_play'), self.onMediaPlay)
|
||||
QtCore.QObject.connect(Receiver.get_receiver(),
|
||||
QtCore.SIGNAL(u'videodisplay_pause'), self.onMediaPause)
|
||||
QtCore.QObject.connect(Receiver.get_receiver(),
|
||||
QtCore.SIGNAL(u'videodisplay_stop'), self.onMediaStop)
|
||||
QtCore.QObject.connect(Receiver.get_receiver(),
|
||||
QtCore.SIGNAL(u'videodisplay_background'), self.onMediaBackground)
|
||||
QtCore.QObject.connect(Receiver.get_receiver(),
|
||||
QtCore.SIGNAL(u'config_updated'), self.setup)
|
||||
QtCore.QObject.connect(self.mediaObject,
|
||||
QtCore.SIGNAL(u'finished()'), self.onMediaBackground)
|
||||
self.setVisible(False)
|
||||
|
||||
def keyPressEvent(self, event):
|
||||
if type(event) == QtGui.QKeyEvent:
|
||||
#here accept the event and do something
|
||||
if event.key() == QtCore.Qt.Key_Escape:
|
||||
self.onMediaStop()
|
||||
event.accept()
|
||||
event.ignore()
|
||||
else:
|
||||
self.displayBlank = False
|
||||
if self.waitingFrame:
|
||||
self.frameView(self.waitingFrame, self.waitingFrameTrans)
|
||||
elif self.display_frame:
|
||||
self.frameView(self.display_frame)
|
||||
event.ignore()
|
||||
|
||||
def setup(self):
|
||||
"""
|
||||
Sets up the screen on a particular screen.
|
||||
"""
|
||||
log.debug(u'VideoDisplay Setup %s for %s ' % (self.screens,
|
||||
self.screens.monitor_number))
|
||||
self.screen = self.screens.current
|
||||
#Sort out screen locations and sizes
|
||||
self.setGeometry(self.screen[u'size'])
|
||||
# To display or not to display?
|
||||
if not self.screen[u'primary'] and self.isVisible():
|
||||
self.showFullScreen()
|
||||
self.primary = False
|
||||
else:
|
||||
self.setVisible(False)
|
||||
self.primary = True
|
||||
|
||||
def onMediaBackground(self, message=None):
|
||||
"""
|
||||
Play a video triggered from the video plugin with the
|
||||
file name passed in on the event.
|
||||
Also triggered from the Finish event so the video will loop
|
||||
if it is triggered from the plugin
|
||||
"""
|
||||
log.debug(u'VideoDisplay Queue new media message %s' % message)
|
||||
#If not file take the stored one
|
||||
if not message:
|
||||
message = self.message
|
||||
# still no file name then stop as it was a normal video stopping
|
||||
if message:
|
||||
self.mediaObject.setCurrentSource(Phonon.MediaSource(message))
|
||||
self.message = message
|
||||
self._play()
|
||||
|
||||
def onMediaQueue(self, message):
|
||||
log.debug(u'Queue new media message %s' % message)
|
||||
self.display_image.close()
|
||||
self.display_text.close()
|
||||
self.display_alert.close()
|
||||
file = os.path.join(message[1], message[2])
|
||||
if self.firstTime:
|
||||
self.mediaObject.setCurrentSource(Phonon.MediaSource(file))
|
||||
self.firstTime = False
|
||||
else:
|
||||
self.mediaObject.enqueue(Phonon.MediaSource(file))
|
||||
self.onMediaPlay()
|
||||
"""
|
||||
Set up a video to play from the serviceitem.
|
||||
"""
|
||||
log.debug(u'VideoDisplay Queue new media message %s' % message)
|
||||
file = os.path.join(message[0].get_frame_path(),
|
||||
message[0].get_frame_title())
|
||||
self.mediaObject.setCurrentSource(Phonon.MediaSource(file))
|
||||
self._play()
|
||||
|
||||
def onMediaPlay(self):
|
||||
log.debug(u'Play the new media, Live ')
|
||||
if not self.mediaLoaded and not self.displayBlank:
|
||||
self.blankDisplay()
|
||||
self.display_frame = self.blankFrame
|
||||
self.firstTime = True
|
||||
self.mediaLoaded = True
|
||||
self.display_image.hide()
|
||||
self.display_text.hide()
|
||||
self.display_alert.hide()
|
||||
self.video.setFullScreen(True)
|
||||
self.video.setVisible(True)
|
||||
"""
|
||||
Respond to the Play button on the slide controller unless the display
|
||||
has been hidden by the slidecontroller
|
||||
"""
|
||||
if not self.hidden:
|
||||
log.debug(u'VideoDisplay Play the new media, Live ')
|
||||
self._play()
|
||||
|
||||
def _play(self):
|
||||
"""
|
||||
We want to play the video so start it and display the screen
|
||||
"""
|
||||
log.debug(u'VideoDisplay _play called')
|
||||
self.mediaObject.play()
|
||||
self.setVisible(True)
|
||||
self.hide()
|
||||
self.showFullScreen()
|
||||
|
||||
def onMediaPause(self):
|
||||
log.debug(u'Media paused by user')
|
||||
"""
|
||||
Pause the video and refresh the screen
|
||||
"""
|
||||
log.debug(u'VideoDisplay Media paused by user')
|
||||
self.mediaObject.pause()
|
||||
self.show()
|
||||
|
||||
def onMediaStop(self):
|
||||
log.debug(u'Media stopped by user')
|
||||
"""
|
||||
Stop the video and clean up
|
||||
"""
|
||||
log.debug(u'VideoDisplay Media stopped by user')
|
||||
self.message = None
|
||||
self.mediaObject.stop()
|
||||
self.onMediaFinish()
|
||||
|
||||
def onMediaFinish(self):
|
||||
log.debug(u'Reached end of media playlist')
|
||||
self.mediaObject.stop()
|
||||
"""
|
||||
Clean up the Object queue
|
||||
"""
|
||||
log.debug(u'VideoDisplay Reached end of media playlist')
|
||||
self.mediaObject.clearQueue()
|
||||
self.mediaLoaded = False
|
||||
self.video.setVisible(False)
|
||||
self.display_text.show()
|
||||
self.display_image.show()
|
||||
self.blankDisplay(False, False)
|
||||
self.setVisible(False)
|
||||
|
||||
def mediaHide(self):
|
||||
"""
|
||||
Hide the video display
|
||||
"""
|
||||
self.mediaObject.pause()
|
||||
self.hidden = True
|
||||
self.setVisible(False)
|
||||
|
||||
def mediaShow(self):
|
||||
"""
|
||||
Show the video disaply if it was already hidden
|
||||
"""
|
||||
if self.hidden:
|
||||
self.hidden = False
|
||||
self._play()
|
||||
|
@ -1,4 +1,5 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
# -*- coding: utf-8 -*-
|
||||
# vim: autoindent shiftwidth=4 expandtab textwidth=80 tabstop=4 softtabstop=4
|
||||
|
||||
###############################################################################
|
||||
@ -28,12 +29,11 @@ import time
|
||||
|
||||
from PyQt4 import QtCore, QtGui
|
||||
|
||||
from openlp.core.ui import AboutForm, SettingsForm, \
|
||||
ServiceManager, ThemeManager, MainDisplay, SlideController, \
|
||||
PluginForm, MediaDockManager
|
||||
from openlp.core.lib import RenderManager, PluginConfig, build_icon, \
|
||||
OpenLPDockWidget, SettingsManager, PluginManager, Receiver, str_to_bool
|
||||
from openlp.core.utils import check_latest_version, AppLocation
|
||||
from openlp.core.ui import AboutForm, SettingsForm, ServiceManager, \
|
||||
ThemeManager, SlideController, PluginForm, MediaDockManager, DisplayManager
|
||||
from openlp.core.lib import RenderManager, build_icon, OpenLPDockWidget, \
|
||||
SettingsManager, PluginManager, Receiver, translate
|
||||
from openlp.core.utils import check_latest_version, AppLocation, add_actions, LanguageManager
|
||||
|
||||
log = logging.getLogger(__name__)
|
||||
|
||||
@ -57,23 +57,21 @@ class VersionThread(QtCore.QThread):
|
||||
A special Qt thread class to fetch the version of OpenLP from the website.
|
||||
This is threaded so that it doesn't affect the loading time of OpenLP.
|
||||
"""
|
||||
def __init__(self, parent, app_version, generalConfig):
|
||||
def __init__(self, parent, app_version):
|
||||
QtCore.QThread.__init__(self, parent)
|
||||
self.parent = parent
|
||||
self.app_version = app_version
|
||||
self.generalConfig = generalConfig
|
||||
|
||||
def run(self):
|
||||
"""
|
||||
Run the thread.
|
||||
"""
|
||||
time.sleep(1)
|
||||
Receiver.send_message(u'blank_check')
|
||||
version = check_latest_version(self.generalConfig, self.app_version)
|
||||
Receiver.send_message(u'maindisplay_blank_check')
|
||||
version = check_latest_version(self.app_version)
|
||||
#new version has arrived
|
||||
if version != self.app_version[u'full']:
|
||||
Receiver.send_message(u'version_check', u'%s' % version)
|
||||
|
||||
Receiver.send_message(u'openlp_version_check', u'%s' % version)
|
||||
|
||||
class Ui_MainWindow(object):
|
||||
def setupUi(self, MainWindow):
|
||||
@ -164,7 +162,6 @@ class Ui_MainWindow(object):
|
||||
self.MediaManagerDock.setWidget(self.MediaManagerContents)
|
||||
MainWindow.addDockWidget(
|
||||
QtCore.Qt.DockWidgetArea(1), self.MediaManagerDock)
|
||||
self.MediaManagerDock.setVisible(self.settingsmanager.showMediaManager)
|
||||
# Create the service manager
|
||||
self.ServiceManagerDock = OpenLPDockWidget(MainWindow)
|
||||
ServiceManagerIcon = build_icon(u':/system/system_servicemanager.png')
|
||||
@ -176,18 +173,17 @@ class Ui_MainWindow(object):
|
||||
self.ServiceManagerDock.setWidget(self.ServiceManagerContents)
|
||||
MainWindow.addDockWidget(
|
||||
QtCore.Qt.DockWidgetArea(2), self.ServiceManagerDock)
|
||||
self.ServiceManagerDock.setVisible(
|
||||
self.settingsmanager.showServiceManager)
|
||||
# Create the theme manager
|
||||
self.ThemeManagerDock = OpenLPDockWidget(MainWindow)
|
||||
ThemeManagerIcon = build_icon(u':/system/system_thememanager.png')
|
||||
self.ThemeManagerDock.setWindowIcon(ThemeManagerIcon)
|
||||
self.ThemeManagerDock.setObjectName(u'ThemeManagerDock')
|
||||
self.ThemeManagerDock.setMinimumWidth(
|
||||
self.settingsmanager.mainwindow_right)
|
||||
self.ThemeManagerContents = ThemeManager(self)
|
||||
self.ThemeManagerDock.setWidget(self.ThemeManagerContents)
|
||||
MainWindow.addDockWidget(
|
||||
QtCore.Qt.DockWidgetArea(2), self.ThemeManagerDock)
|
||||
self.ThemeManagerDock.setVisible(self.settingsmanager.showThemeManager)
|
||||
# Create the menu items
|
||||
self.FileNewItem = QtGui.QAction(MainWindow)
|
||||
self.FileNewItem.setIcon(
|
||||
@ -226,20 +222,18 @@ class Ui_MainWindow(object):
|
||||
self.OptionsSettingsItem.setObjectName(u'OptionsSettingsItem')
|
||||
self.ViewMediaManagerItem = QtGui.QAction(MainWindow)
|
||||
self.ViewMediaManagerItem.setCheckable(True)
|
||||
self.ViewMediaManagerItem.setChecked(
|
||||
self.settingsmanager.showMediaManager)
|
||||
self.ViewMediaManagerItem.setChecked(self.MediaManagerDock.isVisible())
|
||||
self.ViewMediaManagerItem.setIcon(MediaManagerIcon)
|
||||
self.ViewMediaManagerItem.setObjectName(u'ViewMediaManagerItem')
|
||||
self.ViewThemeManagerItem = QtGui.QAction(MainWindow)
|
||||
self.ViewThemeManagerItem.setCheckable(True)
|
||||
self.ViewThemeManagerItem.setChecked(
|
||||
self.settingsmanager.showThemeManager)
|
||||
self.ViewThemeManagerItem.setChecked(self.ThemeManagerDock.isVisible())
|
||||
self.ViewThemeManagerItem.setIcon(ThemeManagerIcon)
|
||||
self.ViewThemeManagerItem.setObjectName(u'ViewThemeManagerItem')
|
||||
self.ViewServiceManagerItem = QtGui.QAction(MainWindow)
|
||||
self.ViewServiceManagerItem.setCheckable(True)
|
||||
self.ViewServiceManagerItem.setChecked(
|
||||
self.settingsmanager.showServiceManager)
|
||||
self.ServiceManagerDock.isVisible())
|
||||
self.ViewServiceManagerItem.setIcon(ServiceManagerIcon)
|
||||
self.ViewServiceManagerItem.setObjectName(u'ViewServiceManagerItem')
|
||||
self.PluginItem = QtGui.QAction(MainWindow)
|
||||
@ -249,18 +243,32 @@ class Ui_MainWindow(object):
|
||||
ContentsIcon = build_icon(u':/system/system_help_contents.png')
|
||||
self.HelpDocumentationItem.setIcon(ContentsIcon)
|
||||
self.HelpDocumentationItem.setObjectName(u'HelpDocumentationItem')
|
||||
self.HelpDocumentationItem.setEnabled(False)
|
||||
self.HelpAboutItem = QtGui.QAction(MainWindow)
|
||||
AboutIcon = build_icon(u':/system/system_about.png')
|
||||
self.HelpAboutItem.setIcon(AboutIcon)
|
||||
self.HelpAboutItem.setObjectName(u'HelpAboutItem')
|
||||
self.HelpOnlineHelpItem = QtGui.QAction(MainWindow)
|
||||
self.HelpOnlineHelpItem.setObjectName(u'HelpOnlineHelpItem')
|
||||
self.HelpOnlineHelpItem.setEnabled(False)
|
||||
self.HelpWebSiteItem = QtGui.QAction(MainWindow)
|
||||
self.HelpWebSiteItem.setObjectName(u'HelpWebSiteItem')
|
||||
self.LanguageTranslateItem = QtGui.QAction(MainWindow)
|
||||
self.LanguageTranslateItem.setObjectName(u'LanguageTranslateItem')
|
||||
self.LanguageEnglishItem = QtGui.QAction(MainWindow)
|
||||
self.LanguageEnglishItem.setObjectName(u'LanguageEnglishItem')
|
||||
#i18n Language Items
|
||||
self.AutoLanguageItem = QtGui.QAction(MainWindow)
|
||||
self.AutoLanguageItem.setObjectName(u'AutoLanguageItem')
|
||||
self.AutoLanguageItem.setCheckable(True)
|
||||
self.LanguageGroup = QtGui.QActionGroup(MainWindow)
|
||||
qmList = LanguageManager.get_qm_list()
|
||||
savedLanguage = LanguageManager.get_language()
|
||||
self.AutoLanguageItem.setChecked(LanguageManager.AutoLanguage)
|
||||
for key in sorted(qmList.keys()):
|
||||
languageItem = QtGui.QAction(MainWindow)
|
||||
languageItem.setObjectName(key)
|
||||
languageItem.setCheckable(True)
|
||||
if qmList[key] == savedLanguage:
|
||||
languageItem.setChecked(True)
|
||||
add_actions(self.LanguageGroup, [languageItem])
|
||||
self.LanguageGroup.setDisabled(LanguageManager.AutoLanguage)
|
||||
self.ToolsAddToolItem = QtGui.QAction(MainWindow)
|
||||
AddToolIcon = build_icon(u':/tools/tools_add.png')
|
||||
self.ToolsAddToolItem.setIcon(AddToolIcon)
|
||||
@ -274,50 +282,37 @@ class Ui_MainWindow(object):
|
||||
self.settingsmanager.showPreviewPanel)
|
||||
self.ModeLiveItem = QtGui.QAction(MainWindow)
|
||||
self.ModeLiveItem.setObjectName(u'ModeLiveItem')
|
||||
self.FileImportMenu.addAction(self.ImportThemeItem)
|
||||
self.FileImportMenu.addAction(self.ImportLanguageItem)
|
||||
self.FileExportMenu.addAction(self.ExportThemeItem)
|
||||
self.FileExportMenu.addAction(self.ExportLanguageItem)
|
||||
self.FileMenu.addAction(self.FileNewItem)
|
||||
self.FileMenu.addAction(self.FileOpenItem)
|
||||
self.FileMenu.addAction(self.FileSaveItem)
|
||||
self.FileMenu.addAction(self.FileSaveAsItem)
|
||||
self.FileMenu.addSeparator()
|
||||
self.FileMenu.addAction(self.FileImportMenu.menuAction())
|
||||
self.FileMenu.addAction(self.FileExportMenu.menuAction())
|
||||
self.FileMenu.addSeparator()
|
||||
self.FileMenu.addAction(self.FileExitItem)
|
||||
self.ViewModeMenu.addAction(self.ModeLiveItem)
|
||||
self.OptionsViewMenu.addAction(self.ViewModeMenu.menuAction())
|
||||
self.OptionsViewMenu.addSeparator()
|
||||
self.OptionsViewMenu.addAction(self.ViewMediaManagerItem)
|
||||
self.OptionsViewMenu.addAction(self.ViewServiceManagerItem)
|
||||
self.OptionsViewMenu.addAction(self.ViewThemeManagerItem)
|
||||
self.OptionsViewMenu.addSeparator()
|
||||
self.OptionsViewMenu.addAction(self.action_Preview_Panel)
|
||||
self.OptionsLanguageMenu.addAction(self.LanguageEnglishItem)
|
||||
self.OptionsLanguageMenu.addSeparator()
|
||||
self.OptionsLanguageMenu.addAction(self.LanguageTranslateItem)
|
||||
self.OptionsMenu.addAction(self.OptionsLanguageMenu.menuAction())
|
||||
self.OptionsMenu.addAction(self.OptionsViewMenu.menuAction())
|
||||
self.OptionsMenu.addSeparator()
|
||||
self.OptionsMenu.addAction(self.OptionsSettingsItem)
|
||||
self.ToolsMenu.addAction(self.PluginItem)
|
||||
self.ToolsMenu.addSeparator()
|
||||
self.ToolsMenu.addAction(self.ToolsAddToolItem)
|
||||
self.HelpMenu.addAction(self.HelpDocumentationItem)
|
||||
self.HelpMenu.addAction(self.HelpOnlineHelpItem)
|
||||
self.HelpMenu.addSeparator()
|
||||
self.HelpMenu.addAction(self.HelpWebSiteItem)
|
||||
self.HelpMenu.addAction(self.HelpAboutItem)
|
||||
self.MenuBar.addAction(self.FileMenu.menuAction())
|
||||
self.MenuBar.addAction(self.OptionsMenu.menuAction())
|
||||
self.MenuBar.addAction(self.ToolsMenu.menuAction())
|
||||
self.MenuBar.addAction(self.HelpMenu.menuAction())
|
||||
add_actions(self.FileImportMenu,
|
||||
(self.ImportThemeItem, self.ImportLanguageItem))
|
||||
add_actions(self.FileExportMenu,
|
||||
(self.ExportThemeItem, self.ExportLanguageItem))
|
||||
self.FileMenuActions = (self.FileNewItem, self.FileOpenItem,
|
||||
self.FileSaveItem, self.FileSaveAsItem, None,
|
||||
self.FileImportMenu.menuAction(), self.FileExportMenu.menuAction(),
|
||||
self.FileExitItem)
|
||||
add_actions(self.ViewModeMenu, [self.ModeLiveItem])
|
||||
add_actions(self.OptionsViewMenu, (self.ViewModeMenu.menuAction(),
|
||||
None, self.ViewMediaManagerItem, self.ViewServiceManagerItem,
|
||||
self.ViewThemeManagerItem, None, self.action_Preview_Panel))
|
||||
#i18n add Language Actions
|
||||
add_actions(self.OptionsLanguageMenu, (self.AutoLanguageItem, None))
|
||||
add_actions(self.OptionsLanguageMenu, self.LanguageGroup.actions())
|
||||
add_actions(self.OptionsMenu, (self.OptionsLanguageMenu.menuAction(),
|
||||
self.OptionsViewMenu.menuAction(), None, self.OptionsSettingsItem))
|
||||
add_actions(self.ToolsMenu,
|
||||
(self.PluginItem, None, self.ToolsAddToolItem))
|
||||
add_actions(self.HelpMenu,
|
||||
(self.HelpDocumentationItem, self.HelpOnlineHelpItem, None,
|
||||
self.HelpWebSiteItem, self.HelpAboutItem))
|
||||
add_actions(self.MenuBar,
|
||||
(self.FileMenu.menuAction(), self.OptionsMenu.menuAction(),
|
||||
self.ToolsMenu.menuAction(), self.HelpMenu.menuAction()))
|
||||
# Initialise the translation
|
||||
self.retranslateUi(MainWindow)
|
||||
self.MediaToolBox.setCurrentIndex(0)
|
||||
# Connect up some signals and slots
|
||||
QtCore.QObject.connect(self.FileMenu,
|
||||
QtCore.SIGNAL(u'aboutToShow()'), self.updateFileMenu)
|
||||
QtCore.QObject.connect(self.FileExitItem,
|
||||
QtCore.SIGNAL(u'triggered()'), MainWindow.close)
|
||||
QtCore.QObject.connect(self.ControlSplitter,
|
||||
@ -335,95 +330,101 @@ class Ui_MainWindow(object):
|
||||
"""
|
||||
Set up the translation system
|
||||
"""
|
||||
MainWindow.mainTitle = self.trUtf8('OpenLP 2.0')
|
||||
MainWindow.defaultThemeText = self.trUtf8(
|
||||
MainWindow.mainTitle = translate('MainWindow', 'OpenLP 2.0')
|
||||
MainWindow.language = translate('MainWindow', 'English')
|
||||
MainWindow.defaultThemeText = translate('MainWindow',
|
||||
'Default Theme: ')
|
||||
MainWindow.setWindowTitle(MainWindow.mainTitle)
|
||||
self.FileMenu.setTitle(self.trUtf8('&File'))
|
||||
self.FileImportMenu.setTitle(self.trUtf8('&Import'))
|
||||
self.FileExportMenu.setTitle(self.trUtf8('&Export'))
|
||||
self.OptionsMenu.setTitle(self.trUtf8('&Options'))
|
||||
self.OptionsViewMenu.setTitle(self.trUtf8('&View'))
|
||||
self.ViewModeMenu.setTitle(self.trUtf8('M&ode'))
|
||||
self.OptionsLanguageMenu.setTitle(self.trUtf8(
|
||||
self.FileMenu.setTitle(translate('MainWindow', '&File'))
|
||||
self.FileImportMenu.setTitle(translate('MainWindow', '&Import'))
|
||||
self.FileExportMenu.setTitle(translate('MainWindow', '&Export'))
|
||||
self.OptionsMenu.setTitle(translate('MainWindow', '&Options'))
|
||||
self.OptionsViewMenu.setTitle(translate('MainWindow', '&View'))
|
||||
self.ViewModeMenu.setTitle(translate('MainWindow', 'M&ode'))
|
||||
self.OptionsLanguageMenu.setTitle(translate('MainWindow',
|
||||
u'&Language'))
|
||||
self.ToolsMenu.setTitle(self.trUtf8('&Tools'))
|
||||
self.HelpMenu.setTitle(self.trUtf8('&Help'))
|
||||
self.ToolsMenu.setTitle(translate('MainWindow', '&Tools'))
|
||||
self.HelpMenu.setTitle(translate('MainWindow', '&Help'))
|
||||
self.MediaManagerDock.setWindowTitle(
|
||||
self.trUtf8('Media Manager'))
|
||||
translate('MainWindow', 'Media Manager'))
|
||||
self.ServiceManagerDock.setWindowTitle(
|
||||
self.trUtf8('Service Manager'))
|
||||
translate('MainWindow', 'Service Manager'))
|
||||
self.ThemeManagerDock.setWindowTitle(
|
||||
self.trUtf8('Theme Manager'))
|
||||
self.FileNewItem.setText(self.trUtf8('&New'))
|
||||
self.FileNewItem.setToolTip(self.trUtf8('New Service'))
|
||||
self.FileNewItem.setStatusTip(self.trUtf8('Create a new Service'))
|
||||
self.FileNewItem.setShortcut(self.trUtf8('Ctrl+N'))
|
||||
self.FileOpenItem.setText(self.trUtf8('&Open'))
|
||||
self.FileOpenItem.setToolTip(self.trUtf8('Open Service'))
|
||||
self.FileOpenItem.setStatusTip(self.trUtf8('Open an existing service'))
|
||||
self.FileOpenItem.setShortcut(self.trUtf8('Ctrl+O'))
|
||||
self.FileSaveItem.setText(self.trUtf8('&Save'))
|
||||
self.FileSaveItem.setToolTip(self.trUtf8('Save Service'))
|
||||
translate('MainWindow', 'Theme Manager'))
|
||||
self.FileNewItem.setText(translate('MainWindow', '&New'))
|
||||
self.FileNewItem.setToolTip(translate('MainWindow', 'New Service'))
|
||||
self.FileNewItem.setStatusTip(translate('MainWindow', 'Create a new Service'))
|
||||
self.FileNewItem.setShortcut(translate('MainWindow', 'Ctrl+N'))
|
||||
self.FileOpenItem.setText(translate('MainWindow', '&Open'))
|
||||
self.FileOpenItem.setToolTip(translate('MainWindow', 'Open Service'))
|
||||
self.FileOpenItem.setStatusTip(translate('MainWindow', 'Open an existing service'))
|
||||
self.FileOpenItem.setShortcut(translate('MainWindow', 'Ctrl+O'))
|
||||
self.FileSaveItem.setText(translate('MainWindow', '&Save'))
|
||||
self.FileSaveItem.setToolTip(translate('MainWindow', 'Save Service'))
|
||||
self.FileSaveItem.setStatusTip(
|
||||
self.trUtf8('Save the current service to disk'))
|
||||
self.FileSaveItem.setShortcut(self.trUtf8('Ctrl+S'))
|
||||
self.FileSaveAsItem.setText(self.trUtf8('Save &As...'))
|
||||
self.FileSaveAsItem.setToolTip(self.trUtf8('Save Service As'))
|
||||
translate('MainWindow', 'Save the current service to disk'))
|
||||
self.FileSaveItem.setShortcut(translate('MainWindow', 'Ctrl+S'))
|
||||
self.FileSaveAsItem.setText(translate('MainWindow', 'Save &As...'))
|
||||
self.FileSaveAsItem.setToolTip(translate('MainWindow', 'Save Service As'))
|
||||
self.FileSaveAsItem.setStatusTip(
|
||||
self.trUtf8('Save the current service under a new name'))
|
||||
self.FileSaveAsItem.setShortcut(self.trUtf8('F12'))
|
||||
self.FileExitItem.setText(self.trUtf8('E&xit'))
|
||||
self.FileExitItem.setStatusTip(self.trUtf8('Quit OpenLP'))
|
||||
self.FileExitItem.setShortcut(self.trUtf8('Alt+F4'))
|
||||
self.ImportThemeItem.setText(self.trUtf8('&Theme'))
|
||||
self.ImportLanguageItem.setText(self.trUtf8('&Language'))
|
||||
self.ExportThemeItem.setText(self.trUtf8('&Theme'))
|
||||
self.ExportLanguageItem.setText(self.trUtf8('&Language'))
|
||||
self.actionLook_Feel.setText(self.trUtf8('Look && &Feel'))
|
||||
self.OptionsSettingsItem.setText(self.trUtf8('&Settings'))
|
||||
self.ViewMediaManagerItem.setText(self.trUtf8('&Media Manager'))
|
||||
self.ViewMediaManagerItem.setToolTip(self.trUtf8('Toggle Media Manager'))
|
||||
translate('MainWindow', 'Save the current service under a new name'))
|
||||
self.FileSaveAsItem.setShortcut(translate('MainWindow', 'F12'))
|
||||
self.FileExitItem.setText(translate('MainWindow', 'E&xit'))
|
||||
self.FileExitItem.setStatusTip(translate('MainWindow', 'Quit OpenLP'))
|
||||
self.FileExitItem.setShortcut(translate('MainWindow', 'Alt+F4'))
|
||||
self.ImportThemeItem.setText(translate('MainWindow', '&Theme'))
|
||||
self.ImportLanguageItem.setText(translate('MainWindow', '&Language'))
|
||||
self.ExportThemeItem.setText(translate('MainWindow', '&Theme'))
|
||||
self.ExportLanguageItem.setText(translate('MainWindow', '&Language'))
|
||||
self.actionLook_Feel.setText(translate('MainWindow', 'Look && &Feel'))
|
||||
self.OptionsSettingsItem.setText(translate('MainWindow', '&Settings'))
|
||||
self.ViewMediaManagerItem.setText(translate('MainWindow', '&Media Manager'))
|
||||
self.ViewMediaManagerItem.setToolTip(
|
||||
translate('MainWindow', 'Toggle Media Manager'))
|
||||
self.ViewMediaManagerItem.setStatusTip(
|
||||
self.trUtf8('Toggle the visibility of the Media Manager'))
|
||||
self.ViewMediaManagerItem.setShortcut(self.trUtf8('F8'))
|
||||
self.ViewThemeManagerItem.setText(self.trUtf8('&Theme Manager'))
|
||||
self.ViewThemeManagerItem.setToolTip(self.trUtf8('Toggle Theme Manager'))
|
||||
translate('MainWindow', 'Toggle the visibility of the Media Manager'))
|
||||
self.ViewMediaManagerItem.setShortcut(translate('MainWindow', 'F8'))
|
||||
self.ViewThemeManagerItem.setText(translate('MainWindow', '&Theme Manager'))
|
||||
self.ViewThemeManagerItem.setToolTip(
|
||||
translate('MainWindow', 'Toggle Theme Manager'))
|
||||
self.ViewThemeManagerItem.setStatusTip(
|
||||
self.trUtf8('Toggle the visibility of the Theme Manager'))
|
||||
self.ViewThemeManagerItem.setShortcut(self.trUtf8('F10'))
|
||||
self.ViewServiceManagerItem.setText(self.trUtf8('&Service Manager'))
|
||||
translate('MainWindow', 'Toggle the visibility of the Theme Manager'))
|
||||
self.ViewThemeManagerItem.setShortcut(translate('MainWindow', 'F10'))
|
||||
self.ViewServiceManagerItem.setText(translate('MainWindow', '&Service Manager'))
|
||||
self.ViewServiceManagerItem.setToolTip(
|
||||
self.trUtf8('Toggle Service Manager'))
|
||||
translate('MainWindow', 'Toggle Service Manager'))
|
||||
self.ViewServiceManagerItem.setStatusTip(
|
||||
self.trUtf8('Toggle the visibility of the Service Manager'))
|
||||
self.ViewServiceManagerItem.setShortcut(self.trUtf8('F9'))
|
||||
self.action_Preview_Panel.setText(self.trUtf8('&Preview Panel'))
|
||||
self.action_Preview_Panel.setToolTip(self.trUtf8('Toggle Preview Panel'))
|
||||
translate('MainWindow', 'Toggle the visibility of the Service Manager'))
|
||||
self.ViewServiceManagerItem.setShortcut(translate('MainWindow', 'F9'))
|
||||
self.action_Preview_Panel.setText(translate('MainWindow', '&Preview Panel'))
|
||||
self.action_Preview_Panel.setToolTip(
|
||||
translate('MainWindow', 'Toggle Preview Panel'))
|
||||
self.action_Preview_Panel.setStatusTip(
|
||||
self.trUtf8('Toggle the visibility of the Preview Panel'))
|
||||
self.action_Preview_Panel.setShortcut(self.trUtf8('F11'))
|
||||
self.PluginItem.setText(self.trUtf8('&Plugin List'))
|
||||
self.PluginItem.setStatusTip(self.trUtf8('List the Plugins'))
|
||||
self.PluginItem.setShortcut(self.trUtf8('Alt+F7'))
|
||||
self.HelpDocumentationItem.setText(self.trUtf8('&User Guide'))
|
||||
self.HelpAboutItem.setText(self.trUtf8('&About'))
|
||||
translate('MainWindow', 'Toggle the visibility of the Preview Panel'))
|
||||
self.action_Preview_Panel.setShortcut(translate('MainWindow', 'F11'))
|
||||
self.PluginItem.setText(translate('MainWindow', '&Plugin List'))
|
||||
self.PluginItem.setStatusTip(translate('MainWindow', 'List the Plugins'))
|
||||
self.PluginItem.setShortcut(translate('MainWindow', 'Alt+F7'))
|
||||
self.HelpDocumentationItem.setText(translate('MainWindow', '&User Guide'))
|
||||
self.HelpAboutItem.setText(translate('MainWindow', '&About'))
|
||||
self.HelpAboutItem.setStatusTip(
|
||||
self.trUtf8('More information about OpenLP'))
|
||||
self.HelpAboutItem.setShortcut(self.trUtf8('Ctrl+F1'))
|
||||
self.HelpOnlineHelpItem.setText(self.trUtf8('&Online Help'))
|
||||
self.HelpWebSiteItem.setText(self.trUtf8('&Web Site'))
|
||||
self.LanguageTranslateItem.setText(self.trUtf8('&Translate'))
|
||||
self.LanguageTranslateItem.setStatusTip(
|
||||
self.trUtf8('Translate the interface to your language'))
|
||||
self.LanguageEnglishItem.setText(self.trUtf8('English'))
|
||||
self.LanguageEnglishItem.setStatusTip(
|
||||
self.trUtf8('Set the interface language to English'))
|
||||
self.ToolsAddToolItem.setText(self.trUtf8('Add &Tool...'))
|
||||
translate('MainWindow', 'More information about OpenLP'))
|
||||
self.HelpAboutItem.setShortcut(translate('MainWindow', 'Ctrl+F1'))
|
||||
self.HelpOnlineHelpItem.setText(translate('MainWindow', '&Online Help'))
|
||||
self.HelpWebSiteItem.setText(translate('MainWindow', '&Web Site'))
|
||||
#i18n
|
||||
self.AutoLanguageItem.setText(translate('MainWindow', '&Auto Detect'))
|
||||
self.AutoLanguageItem.setStatusTip(
|
||||
translate('MainWindow', 'Choose System language, if available'))
|
||||
for item in self.LanguageGroup.actions():
|
||||
item.setText(item.objectName())
|
||||
item.setStatusTip(
|
||||
translate('MainWindow', 'Set the interface language to %1').arg(item.objectName()))
|
||||
self.ToolsAddToolItem.setText(translate('MainWindow', 'Add &Tool...'))
|
||||
self.ToolsAddToolItem.setStatusTip(
|
||||
self.trUtf8('Add an application to the list of tools'))
|
||||
self.action_Preview_Panel.setText(self.trUtf8('&Preview Pane'))
|
||||
self.ModeLiveItem.setText(self.trUtf8('&Live'))
|
||||
translate('MainWindow', 'Add an application to the list of tools'))
|
||||
self.action_Preview_Panel.setText(translate('MainWindow', '&Preview Pane'))
|
||||
self.ModeLiveItem.setText(translate('MainWindow', '&Live'))
|
||||
|
||||
|
||||
class MainWindow(QtGui.QMainWindow, Ui_MainWindow):
|
||||
@ -440,18 +441,28 @@ class MainWindow(QtGui.QMainWindow, Ui_MainWindow):
|
||||
QtGui.QMainWindow.__init__(self)
|
||||
self.screens = screens
|
||||
self.applicationVersion = applicationVersion
|
||||
# Set up settings sections for the main application
|
||||
# (not for use by plugins)
|
||||
self.uiSettingsSection = u'user interface'
|
||||
self.generalSettingsSection = u'general'
|
||||
self.serviceSettingsSection = u'servicemanager'
|
||||
self.songsSettingsSection = u'songs'
|
||||
self.serviceNotSaved = False
|
||||
self.settingsmanager = SettingsManager(screens)
|
||||
self.generalConfig = PluginConfig(u'General')
|
||||
self.mainDisplay = MainDisplay(self, screens)
|
||||
self.displayManager = DisplayManager(screens)
|
||||
self.aboutForm = AboutForm(self, applicationVersion)
|
||||
self.settingsForm = SettingsForm(self.screens, self, self)
|
||||
self.recentFiles = []
|
||||
# Set up the path with plugins
|
||||
pluginpath = AppLocation.get_directory(AppLocation.PluginsDir)
|
||||
self.plugin_manager = PluginManager(pluginpath)
|
||||
self.plugin_helpers = {}
|
||||
# Set up the interface
|
||||
self.setupUi(self)
|
||||
# Load settings after setupUi so default UI sizes are overwritten
|
||||
self.loadSettings()
|
||||
# Once settings are loaded update FileMenu with recentFiles
|
||||
self.updateFileMenu()
|
||||
self.pluginForm = PluginForm(self)
|
||||
# Set up signals and slots
|
||||
QtCore.QObject.connect(self.ImportThemeItem,
|
||||
@ -484,6 +495,8 @@ class MainWindow(QtGui.QMainWindow, Ui_MainWindow):
|
||||
QtCore.QObject.connect(self.PreviewController.Panel,
|
||||
QtCore.SIGNAL(u'visibilityChanged(bool)'),
|
||||
self.action_Preview_Panel.setChecked)
|
||||
QtCore.QObject.connect(self.HelpWebSiteItem,
|
||||
QtCore.SIGNAL(u'triggered()'), self.onHelpWebSiteClicked)
|
||||
QtCore.QObject.connect(self.HelpAboutItem,
|
||||
QtCore.SIGNAL(u'triggered()'), self.onHelpAboutItemClicked)
|
||||
QtCore.QObject.connect(self.PluginItem,
|
||||
@ -491,11 +504,15 @@ class MainWindow(QtGui.QMainWindow, Ui_MainWindow):
|
||||
QtCore.QObject.connect(self.OptionsSettingsItem,
|
||||
QtCore.SIGNAL(u'triggered()'), self.onOptionsSettingsItemClicked)
|
||||
QtCore.QObject.connect(Receiver.get_receiver(),
|
||||
QtCore.SIGNAL(u'update_global_theme'), self.defaultThemeChanged)
|
||||
QtCore.SIGNAL(u'theme_update_global'), self.defaultThemeChanged)
|
||||
QtCore.QObject.connect(Receiver.get_receiver(),
|
||||
QtCore.SIGNAL(u'version_check'), self.versionCheck)
|
||||
QtCore.SIGNAL(u'openlp_version_check'), self.versionCheck)
|
||||
QtCore.QObject.connect(Receiver.get_receiver(),
|
||||
QtCore.SIGNAL(u'blank_check'), self.blankCheck)
|
||||
QtCore.SIGNAL(u'maindisplay_blank_check'), self.blankCheck)
|
||||
QtCore.QObject.connect(Receiver.get_receiver(),
|
||||
QtCore.SIGNAL(u'config_screen_changed'), self.screenChanged)
|
||||
QtCore.QObject.connect(Receiver.get_receiver(),
|
||||
QtCore.SIGNAL(u'maindisplay_status_text'), self.showStatusMessage)
|
||||
QtCore.QObject.connect(self.FileNewItem,
|
||||
QtCore.SIGNAL(u'triggered()'),
|
||||
self.ServiceManagerContents.onNewService)
|
||||
@ -508,11 +525,17 @@ class MainWindow(QtGui.QMainWindow, Ui_MainWindow):
|
||||
QtCore.QObject.connect(self.FileSaveAsItem,
|
||||
QtCore.SIGNAL(u'triggered()'),
|
||||
self.ServiceManagerContents.onSaveService)
|
||||
#i18n set signals for languages
|
||||
QtCore.QObject.connect(self.AutoLanguageItem,
|
||||
QtCore.SIGNAL(u'toggled(bool)'),
|
||||
self.setAutoLanguage)
|
||||
self.LanguageGroup.triggered.connect(LanguageManager.set_language)
|
||||
#warning cyclic dependency
|
||||
#RenderManager needs to call ThemeManager and
|
||||
#ThemeManager needs to call RenderManager
|
||||
self.RenderManager = RenderManager(self.ThemeManagerContents,
|
||||
self.screens, self.getMonitorNumber())
|
||||
self.RenderManager = RenderManager(
|
||||
self.ThemeManagerContents, self.screens)
|
||||
self.displayManager.renderManager = self.RenderManager
|
||||
#Define the media Dock Manager
|
||||
self.mediaDockManager = MediaDockManager(self.MediaToolBox)
|
||||
log.info(u'Load Plugins')
|
||||
@ -521,9 +544,9 @@ class MainWindow(QtGui.QMainWindow, Ui_MainWindow):
|
||||
self.plugin_helpers[u'live'] = self.LiveController
|
||||
self.plugin_helpers[u'render'] = self.RenderManager
|
||||
self.plugin_helpers[u'service'] = self.ServiceManagerContents
|
||||
self.plugin_helpers[u'settings'] = self.settingsForm
|
||||
self.plugin_helpers[u'settings form'] = self.settingsForm
|
||||
self.plugin_helpers[u'toolbox'] = self.mediaDockManager
|
||||
self.plugin_helpers[u'maindisplay'] = self.mainDisplay
|
||||
self.plugin_helpers[u'maindisplay'] = self.displayManager.mainDisplay
|
||||
self.plugin_manager.find_plugins(pluginpath, self.plugin_helpers)
|
||||
# hook methods have to happen after find_plugins. Find plugins needs
|
||||
# the controllers hence the hooks have moved from setupUI() to here
|
||||
@ -549,9 +572,16 @@ class MainWindow(QtGui.QMainWindow, Ui_MainWindow):
|
||||
log.info(u'Load data from Settings')
|
||||
self.settingsForm.postSetUp()
|
||||
|
||||
#i18n
|
||||
def setAutoLanguage(self, value):
|
||||
self.LanguageGroup.setDisabled(value)
|
||||
LanguageManager.AutoLanguage = value
|
||||
LanguageManager.set_language(self.LanguageGroup.checkedAction())
|
||||
|
||||
def versionCheck(self, version):
|
||||
"""
|
||||
Checks the version of the Application called from openlp.pyw
|
||||
Triggered by delay thread.
|
||||
"""
|
||||
app_version = self.applicationVersion[u'full']
|
||||
version_text = unicode(self.trUtf8('Version %s of OpenLP is now '
|
||||
@ -563,45 +593,52 @@ class MainWindow(QtGui.QMainWindow, Ui_MainWindow):
|
||||
QtGui.QMessageBox.StandardButtons(QtGui.QMessageBox.Ok),
|
||||
QtGui.QMessageBox.Ok)
|
||||
|
||||
def getMonitorNumber(self):
|
||||
"""
|
||||
Set up the default behaviour of the monitor configuration in
|
||||
here. Currently it is set to default to monitor 0 if the saved
|
||||
monitor number does not exist.
|
||||
"""
|
||||
screen_number = int(self.generalConfig.get_config(u'monitor', 0))
|
||||
if not self.screens.screen_exists(screen_number):
|
||||
screen_number = 0
|
||||
return screen_number
|
||||
|
||||
def show(self):
|
||||
"""
|
||||
Show the main form, as well as the display form
|
||||
"""
|
||||
self.showMaximized()
|
||||
screen_number = self.getMonitorNumber()
|
||||
self.mainDisplay.setup(screen_number)
|
||||
if self.mainDisplay.isVisible():
|
||||
self.mainDisplay.setFocus()
|
||||
QtGui.QWidget.show(self)
|
||||
#screen_number = self.getMonitorNumber()
|
||||
self.displayManager.setup()
|
||||
if self.displayManager.mainDisplay.isVisible():
|
||||
self.displayManager.mainDisplay.setFocus()
|
||||
self.activateWindow()
|
||||
if str_to_bool(self.generalConfig.get_config(u'auto open', False)):
|
||||
if QtCore.QSettings().value(
|
||||
self.generalSettingsSection + u'/auto open',
|
||||
QtCore.QVariant(False)).toBool():
|
||||
self.ServiceManagerContents.onLoadService(True)
|
||||
|
||||
def blankCheck(self):
|
||||
if str_to_bool(self.generalConfig.get_config(u'screen blank', False)) \
|
||||
and str_to_bool(self.generalConfig.get_config(u'blank warning', False)):
|
||||
"""
|
||||
Check and display message if screen blank on setup.
|
||||
Triggered by delay thread.
|
||||
"""
|
||||
settings = QtCore.QSettings()
|
||||
settings.beginGroup(self.generalSettingsSection)
|
||||
if settings.value(u'screen blank', QtCore.QVariant(False)).toBool() \
|
||||
and settings.value(u'blank warning', QtCore.QVariant(False)).toBool():
|
||||
self.LiveController.onBlankDisplay(True)
|
||||
QtGui.QMessageBox.question(self,
|
||||
self.trUtf8('OpenLP Main Display Blanked'),
|
||||
self.trUtf8('The Main Display has been blanked out'),
|
||||
QtGui.QMessageBox.StandardButtons(QtGui.QMessageBox.Ok),
|
||||
QtGui.QMessageBox.Ok)
|
||||
settings.endGroup()
|
||||
|
||||
def versionThread(self):
|
||||
#app_version = self.applicationVersion[u'full']
|
||||
vT = VersionThread(self, self.applicationVersion, self.generalConfig)
|
||||
"""
|
||||
Start an initial setup thread to delay notifications
|
||||
"""
|
||||
vT = VersionThread(self, self.applicationVersion)
|
||||
vT.start()
|
||||
|
||||
def onHelpWebSiteClicked(self):
|
||||
"""
|
||||
Load the OpenLP website
|
||||
"""
|
||||
import webbrowser
|
||||
webbrowser.open_new(u'http://openlp.org/')
|
||||
|
||||
def onHelpAboutItemClicked(self):
|
||||
"""
|
||||
Show the About form
|
||||
@ -621,13 +658,15 @@ class MainWindow(QtGui.QMainWindow, Ui_MainWindow):
|
||||
Show the Settings dialog
|
||||
"""
|
||||
self.settingsForm.exec_()
|
||||
updated_display = self.getMonitorNumber()
|
||||
if updated_display != self.screens.current_display:
|
||||
self.screens.set_current_display(updated_display)
|
||||
self.RenderManager.update_display(updated_display)
|
||||
self.mainDisplay.setup(updated_display)
|
||||
#Trigger after changes have been made
|
||||
Receiver.send_message(u'config_updated')
|
||||
|
||||
def screenChanged(self):
|
||||
"""
|
||||
The screen has changed to so tell the displays to update_display
|
||||
their locations
|
||||
"""
|
||||
self.RenderManager.update_display()
|
||||
self.displayManager.setup()
|
||||
self.setFocus()
|
||||
self.activateWindow()
|
||||
|
||||
def closeEvent(self, event):
|
||||
@ -637,7 +676,8 @@ class MainWindow(QtGui.QMainWindow, Ui_MainWindow):
|
||||
if self.serviceNotSaved:
|
||||
ret = QtGui.QMessageBox.question(self,
|
||||
self.trUtf8('Save Changes to Service?'),
|
||||
self.trUtf8('Your service has changed, do you want to save those changes?'),
|
||||
self.trUtf8('Your service has changed. '
|
||||
'Do you want to save those changes?'),
|
||||
QtGui.QMessageBox.StandardButtons(
|
||||
QtGui.QMessageBox.Cancel |
|
||||
QtGui.QMessageBox.Discard |
|
||||
@ -645,17 +685,14 @@ class MainWindow(QtGui.QMainWindow, Ui_MainWindow):
|
||||
QtGui.QMessageBox.Save)
|
||||
if ret == QtGui.QMessageBox.Save:
|
||||
self.ServiceManagerContents.onSaveService()
|
||||
self.mainDisplay.close()
|
||||
self.cleanUp()
|
||||
event.accept()
|
||||
elif ret == QtGui.QMessageBox.Discard:
|
||||
self.mainDisplay.close()
|
||||
self.cleanUp()
|
||||
event.accept()
|
||||
else:
|
||||
event.ignore()
|
||||
else:
|
||||
self.mainDisplay.close()
|
||||
self.cleanUp()
|
||||
event.accept()
|
||||
|
||||
@ -668,6 +705,10 @@ class MainWindow(QtGui.QMainWindow, Ui_MainWindow):
|
||||
# Call the cleanup method to shutdown plugins.
|
||||
log.info(u'cleanup plugins')
|
||||
self.plugin_manager.finalise_plugins()
|
||||
# Save settings
|
||||
self.saveSettings()
|
||||
#Close down the displays
|
||||
self.displayManager.close()
|
||||
|
||||
def serviceChanged(self, reset=False, serviceName=None):
|
||||
"""
|
||||
@ -691,6 +732,9 @@ class MainWindow(QtGui.QMainWindow, Ui_MainWindow):
|
||||
title = u'%s - %s*' % (self.mainTitle, service_name)
|
||||
self.setWindowTitle(title)
|
||||
|
||||
def showStatusMessage(self, message):
|
||||
self.StatusBar.showMessage(message)
|
||||
|
||||
def defaultThemeChanged(self, theme):
|
||||
self.DefaultThemeLabel.setText(
|
||||
u'%s %s' % (self.defaultThemeText, theme))
|
||||
@ -698,22 +742,75 @@ class MainWindow(QtGui.QMainWindow, Ui_MainWindow):
|
||||
def toggleMediaManager(self, visible):
|
||||
if self.MediaManagerDock.isVisible() != visible:
|
||||
self.MediaManagerDock.setVisible(visible)
|
||||
self.settingsmanager.setUIItemVisibility(
|
||||
self.MediaManagerDock.objectName(), visible)
|
||||
|
||||
def toggleServiceManager(self, visible):
|
||||
if self.ServiceManagerDock.isVisible() != visible:
|
||||
self.ServiceManagerDock.setVisible(visible)
|
||||
self.settingsmanager.setUIItemVisibility(
|
||||
self.ServiceManagerDock.objectName(), visible)
|
||||
|
||||
def toggleThemeManager(self, visible):
|
||||
if self.ThemeManagerDock.isVisible() != visible:
|
||||
self.ThemeManagerDock.setVisible(visible)
|
||||
self.settingsmanager.setUIItemVisibility(
|
||||
self.ThemeManagerDock.objectName(), visible)
|
||||
|
||||
def togglePreviewPanel(self):
|
||||
previewBool = self.PreviewController.Panel.isVisible()
|
||||
self.PreviewController.Panel.setVisible(not previewBool)
|
||||
self.settingsmanager.togglePreviewPanel(not previewBool)
|
||||
|
||||
def loadSettings(self):
|
||||
log.debug(u'Loading QSettings')
|
||||
settings = QtCore.QSettings()
|
||||
settings.beginGroup(self.generalSettingsSection)
|
||||
self.recentFiles = settings.value(u'recent files').toStringList()
|
||||
settings.endGroup()
|
||||
settings.beginGroup(self.uiSettingsSection)
|
||||
self.move(settings.value(u'main window position',
|
||||
QtCore.QVariant(QtCore.QPoint(0, 0))).toPoint())
|
||||
self.restoreGeometry(
|
||||
settings.value(u'main window geometry').toByteArray())
|
||||
self.restoreState(settings.value(u'main window state').toByteArray())
|
||||
settings.endGroup()
|
||||
|
||||
def saveSettings(self):
|
||||
log.debug(u'Saving QSettings')
|
||||
settings = QtCore.QSettings()
|
||||
settings.beginGroup(self.generalSettingsSection)
|
||||
recentFiles = QtCore.QVariant(self.recentFiles) \
|
||||
if self.recentFiles else QtCore.QVariant()
|
||||
settings.setValue(u'recent files', recentFiles)
|
||||
settings.endGroup()
|
||||
settings.beginGroup(self.uiSettingsSection)
|
||||
settings.setValue(u'main window position',
|
||||
QtCore.QVariant(self.pos()))
|
||||
settings.setValue(u'main window state',
|
||||
QtCore.QVariant(self.saveState()))
|
||||
settings.setValue(u'main window geometry',
|
||||
QtCore.QVariant(self.saveGeometry()))
|
||||
settings.endGroup()
|
||||
|
||||
def updateFileMenu(self):
|
||||
self.FileMenu.clear()
|
||||
add_actions(self.FileMenu, self.FileMenuActions[:-1])
|
||||
existingRecentFiles = []
|
||||
for file in self.recentFiles:
|
||||
if QtCore.QFile.exists(file):
|
||||
existingRecentFiles.append(file)
|
||||
if existingRecentFiles:
|
||||
self.FileMenu.addSeparator()
|
||||
for fileId, filename in enumerate(existingRecentFiles):
|
||||
action = QtGui.QAction(u'&%d %s' % (fileId +1,
|
||||
QtCore.QFileInfo(filename).fileName()), self)
|
||||
action.setData(QtCore.QVariant(filename))
|
||||
self.connect(action, QtCore.SIGNAL(u'triggered()'),
|
||||
self.ServiceManagerContents.loadService)
|
||||
self.FileMenu.addAction(action)
|
||||
self.FileMenu.addSeparator()
|
||||
self.FileMenu.addAction(self.FileMenuActions[-1])
|
||||
|
||||
def addRecentFile(self, filename):
|
||||
recentFileCount = QtCore.QSettings().value(
|
||||
self.generalSettingsSection + u'/max recent files',
|
||||
QtCore.QVariant(4)).toInt()[0]
|
||||
if filename and not self.recentFiles.contains(filename):
|
||||
self.recentFiles.prepend(QtCore.QString(filename))
|
||||
while self.recentFiles.count() > recentFileCount:
|
||||
self.recentFiles.takeLast()
|
||||
|
@ -45,17 +45,17 @@ class MediaDockManager(object):
|
||||
log.debug(u'Inserting %s dock' % media_item.title)
|
||||
match = False
|
||||
for dock_index in range(0, self.media_dock.count()):
|
||||
if self.media_dock.widget(dock_index).ConfigSection == media_item.title.lower():
|
||||
if self.media_dock.widget(dock_index).settingsSection == \
|
||||
media_item.title.lower():
|
||||
match = True
|
||||
break
|
||||
if not match:
|
||||
self.media_dock.addItem(media_item, icon, media_item.title)
|
||||
|
||||
|
||||
def remove_dock(self, name):
|
||||
log.debug(u'remove %s dock' % name)
|
||||
for dock_index in range(0, self.media_dock.count()):
|
||||
if self.media_dock.widget(dock_index):
|
||||
if self.media_dock.widget(dock_index).ConfigSection == name:
|
||||
if self.media_dock.widget(dock_index).settingsSection == name:
|
||||
self.media_dock.widget(dock_index).hide()
|
||||
self.media_dock.removeItem(dock_index)
|
||||
|
@ -24,6 +24,7 @@
|
||||
###############################################################################
|
||||
|
||||
from PyQt4 import QtCore, QtGui
|
||||
from openlp.core.lib import translate
|
||||
|
||||
class Ui_PluginViewDialog(object):
|
||||
def setupUi(self, PluginViewDialog):
|
||||
@ -98,11 +99,11 @@ class Ui_PluginViewDialog(object):
|
||||
QtCore.QMetaObject.connectSlotsByName(PluginViewDialog)
|
||||
|
||||
def retranslateUi(self, PluginViewDialog):
|
||||
PluginViewDialog.setWindowTitle(self.trUtf8('Plugin List'))
|
||||
self.PluginInfoGroupBox.setTitle(self.trUtf8('Plugin Details'))
|
||||
self.VersionLabel.setText(self.trUtf8('Version:'))
|
||||
self.VersionNumberLabel.setText(self.trUtf8('TextLabel'))
|
||||
self.AboutLabel.setText(self.trUtf8('About:'))
|
||||
self.StatusLabel.setText(self.trUtf8('Status:'))
|
||||
self.StatusComboBox.setItemText(0, self.trUtf8('Active'))
|
||||
self.StatusComboBox.setItemText(1, self.trUtf8('Inactive'))
|
||||
PluginViewDialog.setWindowTitle(translate('PluginForm', 'Plugin List'))
|
||||
self.PluginInfoGroupBox.setTitle(translate('PluginForm', 'Plugin Details'))
|
||||
self.VersionLabel.setText(translate('PluginForm', 'Version:'))
|
||||
self.VersionNumberLabel.setText(translate('PluginForm', 'TextLabel'))
|
||||
self.AboutLabel.setText(translate('PluginForm', 'About:'))
|
||||
self.StatusLabel.setText(translate('PluginForm', 'Status:'))
|
||||
self.StatusComboBox.setItemText(0, translate('PluginForm', 'Active'))
|
||||
self.StatusComboBox.setItemText(1, translate('PluginForm', 'Inactive'))
|
||||
|
@ -24,6 +24,7 @@
|
||||
###############################################################################
|
||||
|
||||
import logging
|
||||
import copy
|
||||
|
||||
log = logging.getLogger(__name__)
|
||||
|
||||
@ -36,15 +37,19 @@ class ScreenList(object):
|
||||
def __init__(self):
|
||||
self.preview = None
|
||||
self.current = None
|
||||
self.override = None
|
||||
self.screen_list = []
|
||||
self.count = 0
|
||||
self.display_count = 0
|
||||
#actual display number
|
||||
self.current_display = 0
|
||||
#save config display number
|
||||
self.monitor_number = 0
|
||||
|
||||
def add_screen(self, screen):
|
||||
if screen[u'primary']:
|
||||
self.current = screen
|
||||
self.screen_list.append(screen)
|
||||
self.count += 1
|
||||
self.display_count += 1
|
||||
|
||||
def screen_exists(self, number):
|
||||
for screen in self.screen_list:
|
||||
@ -53,21 +58,35 @@ class ScreenList(object):
|
||||
return False
|
||||
|
||||
def set_current_display(self, number):
|
||||
if number + 1 > self.count:
|
||||
"""
|
||||
Set up the current screen dimensions
|
||||
"""
|
||||
log.debug(u'set_current_display %s', number, )
|
||||
if number + 1 > self.display_count:
|
||||
self.current = self.screen_list[0]
|
||||
self.override = copy.deepcopy(self.current)
|
||||
self.current_display = 0
|
||||
else:
|
||||
self.current = self.screen_list[number]
|
||||
self.preview = self.current
|
||||
self.override = copy.deepcopy(self.current)
|
||||
self.preview = copy.deepcopy(self.current)
|
||||
self.current_display = number
|
||||
if self.count == 1:
|
||||
if self.display_count == 1:
|
||||
self.preview = self.screen_list[0]
|
||||
|
||||
# if self.screen[u'number'] != screenNumber:
|
||||
# # We will most probably never actually hit this bit, but just in
|
||||
# # case the index in the list doesn't match the screen number, we
|
||||
# # search for it.
|
||||
# for scrn in self.screens:
|
||||
# if scrn[u'number'] == screenNumber:
|
||||
# self.screen = scrn
|
||||
# break
|
||||
def set_override_display(self):
|
||||
"""
|
||||
replace the current size with the override values
|
||||
user wants to have their own screen attributes
|
||||
"""
|
||||
log.debug(u'set_override_display')
|
||||
self.current = copy.deepcopy(self.override)
|
||||
self.preview = copy.deepcopy(self.current)
|
||||
|
||||
def reset_current_display(self):
|
||||
"""
|
||||
replace the current values with the correct values
|
||||
user wants to use the correct screen attributes
|
||||
"""
|
||||
log.debug(u'reset_current_display')
|
||||
self.set_current_display(self.current_display)
|
||||
|
@ -24,6 +24,7 @@
|
||||
###############################################################################
|
||||
|
||||
from PyQt4 import QtCore, QtGui
|
||||
from openlp.core.lib import translate
|
||||
|
||||
class Ui_ServiceItemEditDialog(object):
|
||||
def setupUi(self, ServiceItemEditDialog):
|
||||
@ -66,8 +67,8 @@ class Ui_ServiceItemEditDialog(object):
|
||||
QtCore.QMetaObject.connectSlotsByName(ServiceItemEditDialog)
|
||||
|
||||
def retranslateUi(self, ServiceItemEditDialog):
|
||||
ServiceItemEditDialog.setWindowTitle(self.trUtf8('Service Item Maintenance'))
|
||||
self.upButton.setText(self.trUtf8('Up'))
|
||||
self.deleteButton.setText(self.trUtf8('Delete'))
|
||||
self.downButton.setText(self.trUtf8('Down'))
|
||||
ServiceItemEditDialog.setWindowTitle(translate('ServiceItemEditForm', 'Service Item Maintenance'))
|
||||
self.upButton.setText(translate('ServiceItemEditForm', 'Up'))
|
||||
self.deleteButton.setText(translate('ServiceItemEditForm', 'Delete'))
|
||||
self.downButton.setText(translate('ServiceItemEditForm', 'Down'))
|
||||
|
||||
|
@ -32,14 +32,15 @@ log = logging.getLogger(__name__)
|
||||
|
||||
from PyQt4 import QtCore, QtGui
|
||||
|
||||
from openlp.core.lib import PluginConfig, OpenLPToolbar, ServiceItem, \
|
||||
contextMenuAction, Receiver, str_to_bool, build_icon
|
||||
from openlp.core.lib import OpenLPToolbar, ServiceItem, contextMenuAction, \
|
||||
Receiver, build_icon, ItemCapabilities, SettingsManager
|
||||
from openlp.core.ui import ServiceNoteForm, ServiceItemEditForm
|
||||
from openlp.core.utils import AppLocation
|
||||
|
||||
class ServiceManagerList(QtGui.QTreeWidget):
|
||||
|
||||
def __init__(self, parent=None, name=None):
|
||||
QtGui.QTreeWidget.__init__(self,parent)
|
||||
QtGui.QTreeWidget.__init__(self, parent)
|
||||
self.parent = parent
|
||||
|
||||
def keyPressEvent(self, event):
|
||||
@ -83,7 +84,7 @@ class ServiceManagerList(QtGui.QTreeWidget):
|
||||
mimeData = QtCore.QMimeData()
|
||||
drag.setMimeData(mimeData)
|
||||
mimeData.setText(u'ServiceManager')
|
||||
dropAction = drag.start(QtCore.Qt.CopyAction)
|
||||
drag.start(QtCore.Qt.CopyAction)
|
||||
|
||||
class ServiceManager(QtGui.QWidget):
|
||||
"""
|
||||
@ -100,12 +101,10 @@ class ServiceManager(QtGui.QWidget):
|
||||
self.parent = parent
|
||||
self.serviceItems = []
|
||||
self.serviceName = u''
|
||||
self.suffixes = []
|
||||
self.droppos = 0
|
||||
#is a new service and has not been saved
|
||||
self.isNew = True
|
||||
#Indicates if remoteTriggering is active. If it is the next addServiceItem call
|
||||
#will replace the currently selected one.
|
||||
self.remoteEditTriggered = False
|
||||
self.serviceNoteForm = ServiceNoteForm()
|
||||
self.serviceItemEditForm = ServiceItemEditForm()
|
||||
#start with the layout
|
||||
@ -186,29 +185,38 @@ class ServiceManager(QtGui.QWidget):
|
||||
QtCore.QObject.connect(self.ServiceManagerList,
|
||||
QtCore.SIGNAL(u'itemExpanded(QTreeWidgetItem*)'), self.expanded)
|
||||
QtCore.QObject.connect(Receiver.get_receiver(),
|
||||
QtCore.SIGNAL(u'update_themes'), self.updateThemeList)
|
||||
QtCore.QObject.connect(Receiver.get_receiver(),
|
||||
QtCore.SIGNAL(u'remote_edit_clear'), self.onRemoteEditClear)
|
||||
QtCore.QObject.connect(Receiver.get_receiver(),
|
||||
QtCore.SIGNAL(u'presentation types'), self.onPresentationTypes)
|
||||
QtCore.SIGNAL(u'theme_update_list'), self.updateThemeList)
|
||||
QtCore.QObject.connect(Receiver.get_receiver(),
|
||||
QtCore.SIGNAL(u'servicemanager_next_item'), self.nextItem)
|
||||
QtCore.QObject.connect(Receiver.get_receiver(),
|
||||
QtCore.SIGNAL(u'servicemanager_previous_item'), self.previousItem)
|
||||
QtCore.QObject.connect(Receiver.get_receiver(),
|
||||
QtCore.SIGNAL(u'servicemanager_set_item'), self.onSetItem)
|
||||
QtCore.QObject.connect(Receiver.get_receiver(),
|
||||
QtCore.SIGNAL(u'servicemanager_list_request'), self.listRequest)
|
||||
QtCore.QObject.connect(Receiver.get_receiver(),
|
||||
QtCore.SIGNAL(u'config_updated'), self.regenerateServiceItems)
|
||||
# Last little bits of setting up
|
||||
self.config = PluginConfig(u'ServiceManager')
|
||||
self.servicePath = self.config.get_data_path()
|
||||
self.service_theme = unicode(
|
||||
self.config.get_config(u'service theme', u''))
|
||||
self.service_theme = unicode(QtCore.QSettings().value(
|
||||
self.parent.serviceSettingsSection + u'/service theme',
|
||||
QtCore.QVariant(u'')).toString())
|
||||
self.servicePath = AppLocation.get_section_data_path(u'servicemanager')
|
||||
#build the drag and drop context menu
|
||||
self.dndMenu = QtGui.QMenu()
|
||||
self.newAction = self.dndMenu.addAction(self.trUtf8('&Add New Item'))
|
||||
self.newAction.setIcon(build_icon(u':/general/general_edit.png'))
|
||||
self.addToAction = self.dndMenu.addAction(self.trUtf8('&Add to Selected Item'))
|
||||
self.addToAction.setIcon(build_icon(u':/general/general_edit.png'))
|
||||
#build the context menu
|
||||
self.menu = QtGui.QMenu()
|
||||
self.editAction = self.menu.addAction(self.trUtf8('&Edit Item'))
|
||||
self.editAction.setIcon(build_icon(u':/general/general_edit.png'))
|
||||
self.maintainAction = self.menu.addAction(self.trUtf8('&Maintain Item'))
|
||||
self.editAction.setIcon(build_icon(u':/general/general_edit.png'))
|
||||
self.maintainAction.setIcon(build_icon(u':/general/general_edit.png'))
|
||||
self.notesAction = self.menu.addAction(self.trUtf8('&Notes'))
|
||||
self.notesAction.setIcon(build_icon(u':/services/service_notes.png'))
|
||||
self.deleteAction = self.menu.addAction(self.trUtf8('&Delete From Service'))
|
||||
self.deleteAction = self.menu.addAction(
|
||||
self.trUtf8('&Delete From Service'))
|
||||
self.deleteAction.setIcon(build_icon(u':/general/general_delete.png'))
|
||||
self.sep1 = self.menu.addAction(u'')
|
||||
self.sep1.setSeparator(True)
|
||||
@ -221,6 +229,9 @@ class ServiceManager(QtGui.QWidget):
|
||||
self.themeMenu = QtGui.QMenu(self.trUtf8(u'&Change Item Theme'))
|
||||
self.menu.addMenu(self.themeMenu)
|
||||
|
||||
def supportedSuffixes(self, suffix):
|
||||
self.suffixes.append(suffix)
|
||||
|
||||
def contextMenu(self, point):
|
||||
item = self.ServiceManagerList.itemAt(point)
|
||||
if item is None:
|
||||
@ -233,9 +244,10 @@ class ServiceManager(QtGui.QWidget):
|
||||
self.editAction.setVisible(False)
|
||||
self.maintainAction.setVisible(False)
|
||||
self.notesAction.setVisible(False)
|
||||
if serviceItem[u'service_item'].edit_enabled:
|
||||
if serviceItem[u'service_item'].is_capable(ItemCapabilities.AllowsEdit):
|
||||
self.editAction.setVisible(True)
|
||||
if serviceItem[u'service_item'].maintain_allowed:
|
||||
if serviceItem[u'service_item']\
|
||||
.is_capable(ItemCapabilities.AllowsMaintain):
|
||||
self.maintainAction.setVisible(True)
|
||||
if item.parent() is None:
|
||||
self.notesAction.setVisible(True)
|
||||
@ -256,9 +268,6 @@ class ServiceManager(QtGui.QWidget):
|
||||
if action == self.liveAction:
|
||||
self.makeLive()
|
||||
|
||||
def onPresentationTypes(self, presentation_types):
|
||||
self.presentation_types = presentation_types
|
||||
|
||||
def onServiceItemNoteForm(self):
|
||||
item, count = self.findServiceItem()
|
||||
self.serviceNoteForm.textEdit.setPlainText(
|
||||
@ -296,6 +305,41 @@ class ServiceManager(QtGui.QWidget):
|
||||
lookFor = 1
|
||||
serviceIterator += 1
|
||||
|
||||
def previousItem(self):
|
||||
"""
|
||||
Called by the SlideController to select the
|
||||
previous service item
|
||||
"""
|
||||
if len(self.ServiceManagerList.selectedItems()) == 0:
|
||||
return
|
||||
selected = self.ServiceManagerList.selectedItems()[0]
|
||||
prevItem = None
|
||||
serviceIterator = QtGui.QTreeWidgetItemIterator(self.ServiceManagerList)
|
||||
while serviceIterator.value():
|
||||
if serviceIterator.value() == selected:
|
||||
if prevItem:
|
||||
self.ServiceManagerList.setCurrentItem(prevItem)
|
||||
self.makeLive()
|
||||
return
|
||||
if serviceIterator.value().parent() is None:
|
||||
prevItem = serviceIterator.value()
|
||||
serviceIterator += 1
|
||||
|
||||
def onSetItem(self, message):
|
||||
"""
|
||||
Called by a signal to select a specific item
|
||||
"""
|
||||
self.setItem(int(message[0]))
|
||||
|
||||
def setItem(self, index):
|
||||
"""
|
||||
Makes a specific item in the service live
|
||||
"""
|
||||
if index >= 0 and index < self.ServiceManagerList.topLevelItemCount:
|
||||
item = self.ServiceManagerList.topLevelItem(index)
|
||||
self.ServiceManagerList.setCurrentItem(item)
|
||||
self.makeLive()
|
||||
|
||||
def onMoveSelectionUp(self):
|
||||
"""
|
||||
Moves the selection up the window
|
||||
@ -410,13 +454,13 @@ class ServiceManager(QtGui.QWidget):
|
||||
"""
|
||||
Clear the list to create a new service
|
||||
"""
|
||||
if self.parent.serviceNotSaved and \
|
||||
str_to_bool(PluginConfig(u'General').
|
||||
get_config(u'save prompt', u'False')):
|
||||
if self.parent.serviceNotSaved and QtCore.QSettings().value(
|
||||
self.parent.generalSettingsSection + u'/save prompt',
|
||||
QtCore.QVariant(False)).toBool():
|
||||
ret = QtGui.QMessageBox.question(self,
|
||||
self.trUtf8('Save Changes to Service?'),
|
||||
self.trUtf8('Your service is unsaved, do you want to save those '
|
||||
'changes before creating a new one ?'),
|
||||
self.trUtf8('Your service is unsaved, do you want to save '
|
||||
'those changes before creating a new one?'),
|
||||
QtGui.QMessageBox.StandardButtons(
|
||||
QtGui.QMessageBox.Cancel |
|
||||
QtGui.QMessageBox.Save),
|
||||
@ -455,19 +499,22 @@ class ServiceManager(QtGui.QWidget):
|
||||
for itemcount, item in enumerate(self.serviceItems):
|
||||
serviceitem = item[u'service_item']
|
||||
treewidgetitem = QtGui.QTreeWidgetItem(self.ServiceManagerList)
|
||||
if serviceitem.notes:
|
||||
icon = QtGui.QImage(serviceitem.icon)
|
||||
icon = icon.scaled(80, 80, QtCore.Qt.KeepAspectRatio,
|
||||
QtCore.Qt.SmoothTransformation)
|
||||
overlay = QtGui.QImage(':/services/service_item_notes.png')
|
||||
overlay = overlay.scaled(80, 80, QtCore.Qt.KeepAspectRatio,
|
||||
QtCore.Qt.SmoothTransformation)
|
||||
painter = QtGui.QPainter(icon)
|
||||
painter.drawImage(0, 0, overlay)
|
||||
painter.end()
|
||||
treewidgetitem.setIcon(0, build_icon(icon))
|
||||
if serviceitem.is_valid:
|
||||
if serviceitem.notes:
|
||||
icon = QtGui.QImage(serviceitem.icon)
|
||||
icon = icon.scaled(80, 80, QtCore.Qt.KeepAspectRatio,
|
||||
QtCore.Qt.SmoothTransformation)
|
||||
overlay = QtGui.QImage(':/services/service_item_notes.png')
|
||||
overlay = overlay.scaled(80, 80, QtCore.Qt.KeepAspectRatio,
|
||||
QtCore.Qt.SmoothTransformation)
|
||||
painter = QtGui.QPainter(icon)
|
||||
painter.drawImage(0, 0, overlay)
|
||||
painter.end()
|
||||
treewidgetitem.setIcon(0, build_icon(icon))
|
||||
else:
|
||||
treewidgetitem.setIcon(0, serviceitem.iconic_representation)
|
||||
else:
|
||||
treewidgetitem.setIcon(0, serviceitem.iconic_representation)
|
||||
treewidgetitem.setIcon(0, build_icon(u':/general/general_delete.png'))
|
||||
treewidgetitem.setText(0, serviceitem.title)
|
||||
treewidgetitem.setToolTip(0, serviceitem.notes)
|
||||
treewidgetitem.setData(0, QtCore.Qt.UserRole,
|
||||
@ -495,17 +542,21 @@ class ServiceManager(QtGui.QWidget):
|
||||
log.debug(u'onSaveService')
|
||||
if not quick or self.isNew:
|
||||
filename = QtGui.QFileDialog.getSaveFileName(self,
|
||||
self.trUtf8(u'Save Service'), self.config.get_last_dir(),
|
||||
self.trUtf8(u'Save Service'),
|
||||
SettingsManager.get_last_dir(self.parent.serviceSettingsSection),
|
||||
self.trUtf8(u'OpenLP Service Files (*.osz)'))
|
||||
else:
|
||||
filename = self.config.get_last_dir()
|
||||
filename = SettingsManager.get_last_dir(
|
||||
self.parent.serviceSettingsSection)
|
||||
if filename:
|
||||
splittedFile = filename.split(u'.')
|
||||
if splittedFile[-1] != u'osz':
|
||||
filename = filename + u'.osz'
|
||||
filename = unicode(filename)
|
||||
self.isNew = False
|
||||
self.config.set_last_dir(filename)
|
||||
SettingsManager.set_last_dir(
|
||||
self.parent.serviceSettingsSection,
|
||||
os.path.split(filename)[0])
|
||||
service = []
|
||||
servicefile = filename + u'.osd'
|
||||
zip = None
|
||||
@ -513,7 +564,8 @@ class ServiceManager(QtGui.QWidget):
|
||||
try:
|
||||
zip = zipfile.ZipFile(unicode(filename), 'w')
|
||||
for item in self.serviceItems:
|
||||
service.append({u'serviceitem':item[u'service_item'].get_service_repr()})
|
||||
service.append({u'serviceitem':item[u'service_item']
|
||||
.get_service_repr()})
|
||||
if item[u'service_item'].uses_file():
|
||||
for frame in item[u'service_item'].get_frames():
|
||||
path_from = unicode(os.path.join(
|
||||
@ -537,27 +589,52 @@ class ServiceManager(QtGui.QWidget):
|
||||
pass #if not present do not worry
|
||||
name = filename.split(os.path.sep)
|
||||
self.serviceName = name[-1]
|
||||
self.parent.addRecentFile(filename)
|
||||
self.parent.serviceChanged(True, self.serviceName)
|
||||
|
||||
def onQuickSaveService(self):
|
||||
self.onSaveService(True)
|
||||
|
||||
def onLoadService(self, lastService=False):
|
||||
if lastService:
|
||||
filename = SettingsManager.get_last_dir(
|
||||
self.parent.serviceSettingsSection)
|
||||
else:
|
||||
filename = QtGui.QFileDialog.getOpenFileName(
|
||||
self, self.trUtf8('Open Service'),
|
||||
SettingsManager.get_last_dir(
|
||||
self.parent.serviceSettingsSection), u'Services (*.osz)')
|
||||
self.loadService(filename)
|
||||
|
||||
def loadService(self, filename=None):
|
||||
"""
|
||||
Load an existing service from disk and rebuild the serviceitems. All
|
||||
files retrieved from the zip file are placed in a temporary directory
|
||||
and will only be used for this service.
|
||||
"""
|
||||
if lastService:
|
||||
filename = self.config.get_last_dir()
|
||||
else:
|
||||
filename = QtGui.QFileDialog.getOpenFileName(
|
||||
self, self.trUtf8('Open Service'),
|
||||
self.config.get_last_dir(), u'Services (*.osz)')
|
||||
if self.parent.serviceNotSaved:
|
||||
ret = QtGui.QMessageBox.question(self,
|
||||
self.trUtf8('Save Changes to Service?'),
|
||||
self.trUtf8('Your current service is unsaved, do you want to '
|
||||
'save the changes before opening a new one?'),
|
||||
QtGui.QMessageBox.StandardButtons(
|
||||
QtGui.QMessageBox.Discard |
|
||||
QtGui.QMessageBox.Save),
|
||||
QtGui.QMessageBox.Save)
|
||||
if ret == QtGui.QMessageBox.Save:
|
||||
self.onSaveService()
|
||||
if filename is None:
|
||||
action = self.sender()
|
||||
if isinstance(action, QtGui.QAction):
|
||||
filename = action.data().toString()
|
||||
else:
|
||||
return
|
||||
filename = unicode(filename)
|
||||
name = filename.split(os.path.sep)
|
||||
if filename:
|
||||
self.config.set_last_dir(filename)
|
||||
SettingsManager.set_last_dir(
|
||||
self.parent.serviceSettingsSection,
|
||||
os.path.split(filename)[0])
|
||||
zip = None
|
||||
f = None
|
||||
try:
|
||||
@ -581,8 +658,8 @@ class ServiceManager(QtGui.QWidget):
|
||||
serviceitem = ServiceItem()
|
||||
serviceitem.RenderManager = self.parent.RenderManager
|
||||
serviceitem.set_from_service(item, self.servicePath)
|
||||
if self.validateItem(serviceitem):
|
||||
self.addServiceItem(serviceitem)
|
||||
self.validateItem(serviceitem)
|
||||
self.addServiceItem(serviceitem)
|
||||
try:
|
||||
if os.path.isfile(p_file):
|
||||
os.remove(p_file)
|
||||
@ -597,15 +674,18 @@ class ServiceManager(QtGui.QWidget):
|
||||
zip.close()
|
||||
self.isNew = False
|
||||
self.serviceName = name[len(name) - 1]
|
||||
self.parent.addRecentFile(filename)
|
||||
self.parent.serviceChanged(True, self.serviceName)
|
||||
|
||||
def validateItem(self, serviceItem):
|
||||
# print "---"
|
||||
# print serviceItem.name
|
||||
# print serviceItem.title
|
||||
# print serviceItem.service_item_path
|
||||
# print serviceItem.service_item_type
|
||||
return True
|
||||
"""
|
||||
Validates the service item and if the suffix matches an accepted
|
||||
one it allows the item to be displayed
|
||||
"""
|
||||
if serviceItem.is_command():
|
||||
type = serviceItem._raw_frames[0][u'title'].split(u'.')[1]
|
||||
if type not in self.suffixes:
|
||||
serviceItem.is_valid = False
|
||||
|
||||
def cleanUp(self):
|
||||
"""
|
||||
@ -625,7 +705,9 @@ class ServiceManager(QtGui.QWidget):
|
||||
"""
|
||||
self.service_theme = unicode(self.ThemeComboBox.currentText())
|
||||
self.parent.RenderManager.set_service_theme(self.service_theme)
|
||||
self.config.set_config(u'service theme', self.service_theme)
|
||||
QtCore.QSettings().setValue(
|
||||
self.parent.serviceSettingsSection + u'/service theme',
|
||||
QtCore.QVariant(self.service_theme))
|
||||
self.regenerateServiceItems()
|
||||
|
||||
def regenerateServiceItems(self):
|
||||
@ -637,12 +719,13 @@ class ServiceManager(QtGui.QWidget):
|
||||
self.serviceItems = []
|
||||
self.isNew = True
|
||||
for item in tempServiceItems:
|
||||
self.addServiceItem(item[u'service_item'], False, item[u'expanded'])
|
||||
self.addServiceItem(
|
||||
item[u'service_item'], False, item[u'expanded'])
|
||||
#Set to False as items may have changed rendering
|
||||
#does not impact the saved song so True may also be valid
|
||||
self.parent.serviceChanged(False, self.serviceName)
|
||||
|
||||
def addServiceItem(self, item, rebuild=False, expand=True):
|
||||
def addServiceItem(self, item, rebuild=False, expand=True, replace=False):
|
||||
"""
|
||||
Add a Service item to the list
|
||||
|
||||
@ -652,10 +735,9 @@ class ServiceManager(QtGui.QWidget):
|
||||
"""
|
||||
sitem, count = self.findServiceItem()
|
||||
item.render()
|
||||
if self.remoteEditTriggered:
|
||||
if replace:
|
||||
item.merge(self.serviceItems[sitem][u'service_item'])
|
||||
self.serviceItems[sitem][u'service_item'] = item
|
||||
self.remoteEditTriggered = False
|
||||
self.repaintServiceList(sitem + 1, 0)
|
||||
self.parent.LiveController.replaceServiceManagerItem(item)
|
||||
else:
|
||||
@ -687,8 +769,17 @@ class ServiceManager(QtGui.QWidget):
|
||||
Send the current item to the Preview slide controller
|
||||
"""
|
||||
item, count = self.findServiceItem()
|
||||
self.parent.PreviewController.addServiceManagerItem(
|
||||
self.serviceItems[item][u'service_item'], count)
|
||||
if self.serviceItems[item][u'service_item'].is_valid:
|
||||
self.parent.PreviewController.addServiceManagerItem(
|
||||
self.serviceItems[item][u'service_item'], count)
|
||||
else:
|
||||
QtGui.QMessageBox.critical(self,
|
||||
self.trUtf8('Missing Display Handler'),
|
||||
self.trUtf8('Your item cannot be displayed as '
|
||||
'there is no handler to display it'),
|
||||
QtGui.QMessageBox.StandardButtons(
|
||||
QtGui.QMessageBox.Ok),
|
||||
QtGui.QMessageBox.Ok)
|
||||
|
||||
def getServiceItem(self):
|
||||
"""
|
||||
@ -698,8 +789,6 @@ class ServiceManager(QtGui.QWidget):
|
||||
if item == -1:
|
||||
return False
|
||||
else:
|
||||
#Switch on remote edit update functionality.
|
||||
self.remoteEditTriggered = True
|
||||
return self.serviceItems[item][u'service_item']
|
||||
|
||||
def makeLive(self):
|
||||
@ -707,30 +796,38 @@ class ServiceManager(QtGui.QWidget):
|
||||
Send the current item to the Live slide controller
|
||||
"""
|
||||
item, count = self.findServiceItem()
|
||||
self.parent.LiveController.addServiceManagerItem(
|
||||
self.serviceItems[item][u'service_item'], count)
|
||||
if str_to_bool(PluginConfig(u'General').
|
||||
get_config(u'auto preview', u'False')):
|
||||
item += 1
|
||||
if self.serviceItems and item < len(self.serviceItems) and \
|
||||
self.serviceItems[item][u'service_item'].auto_preview_allowed:
|
||||
self.parent.PreviewController.addServiceManagerItem(
|
||||
self.serviceItems[item][u'service_item'], 0)
|
||||
if self.serviceItems[item][u'service_item'].is_valid:
|
||||
self.parent.LiveController.addServiceManagerItem(
|
||||
self.serviceItems[item][u'service_item'], count)
|
||||
if QtCore.QSettings().value(
|
||||
self.parent.generalSettingsSection + u'/auto preview',
|
||||
QtCore.QVariant(False)).toBool():
|
||||
item += 1
|
||||
if self.serviceItems and item < len(self.serviceItems) and \
|
||||
self.serviceItems[item][u'service_item'].is_capable(
|
||||
ItemCapabilities.AllowsPreview):
|
||||
self.parent.PreviewController.addServiceManagerItem(
|
||||
self.serviceItems[item][u'service_item'], 0)
|
||||
else:
|
||||
QtGui.QMessageBox.critical(self,
|
||||
self.trUtf8('Missing Display Handler'),
|
||||
self.trUtf8('Your item cannot be displayed as '
|
||||
'there is no handler to display it'),
|
||||
QtGui.QMessageBox.StandardButtons(
|
||||
QtGui.QMessageBox.Ok),
|
||||
QtGui.QMessageBox.Ok)
|
||||
|
||||
def remoteEdit(self):
|
||||
"""
|
||||
Posts a remote edit message to a plugin to allow item to be edited.
|
||||
"""
|
||||
item, count = self.findServiceItem()
|
||||
if self.serviceItems[item][u'service_item'].edit_enabled:
|
||||
self.remoteEditTriggered = True
|
||||
if self.serviceItems[item][u'service_item']\
|
||||
.is_capable(ItemCapabilities.AllowsEdit):
|
||||
Receiver.send_message(u'%s_edit' %
|
||||
self.serviceItems[item][u'service_item'].name, u'L:%s' %
|
||||
self.serviceItems[item][u'service_item'].name.lower(), u'L:%s' %
|
||||
self.serviceItems[item][u'service_item'].editId )
|
||||
|
||||
def onRemoteEditClear(self):
|
||||
self.remoteEditTriggered = False
|
||||
|
||||
def findServiceItem(self):
|
||||
"""
|
||||
Finds a ServiceItem in the list
|
||||
@ -772,8 +869,9 @@ class ServiceManager(QtGui.QWidget):
|
||||
if link.hasText():
|
||||
plugin = event.mimeData().text()
|
||||
item = self.ServiceManagerList.itemAt(event.pos())
|
||||
#ServiceManager started the drag and drop
|
||||
if plugin == u'ServiceManager':
|
||||
startpos, startCount = self.findServiceItem()
|
||||
startpos, startCount = self.findServiceItem()
|
||||
if item is None:
|
||||
endpos = len(self.serviceItems)
|
||||
else:
|
||||
@ -787,11 +885,28 @@ class ServiceManager(QtGui.QWidget):
|
||||
self.serviceItems.insert(newpos, serviceItem)
|
||||
self.repaintServiceList(endpos, startCount)
|
||||
else:
|
||||
#we are not over anything so drop
|
||||
replace = False
|
||||
if item == None:
|
||||
self.droppos = len(self.serviceItems)
|
||||
else:
|
||||
self.droppos = self._getParentItemData(item)
|
||||
Receiver.send_message(u'%s_add_service_item' % plugin)
|
||||
#we are over somthing so lets investigate
|
||||
pos = self._getParentItemData(item) - 1
|
||||
serviceItem = self.serviceItems[pos]
|
||||
if plugin == serviceItem[u'service_item'].name \
|
||||
and serviceItem[u'service_item'].is_capable(ItemCapabilities.AllowsAdditions):
|
||||
action = self.dndMenu.exec_(QtGui.QCursor.pos())
|
||||
#New action required
|
||||
if action == self.newAction:
|
||||
self.droppos = self._getParentItemData(item)
|
||||
#Append to existing action
|
||||
if action == self.addToAction:
|
||||
self.droppos = self._getParentItemData(item)
|
||||
item.setSelected(True)
|
||||
replace = True
|
||||
else:
|
||||
self.droppos = self._getParentItemData(item)
|
||||
Receiver.send_message(u'%s_add_service_item' % plugin, replace)
|
||||
|
||||
def updateThemeList(self, theme_list):
|
||||
"""
|
||||
@ -832,3 +947,20 @@ class ServiceManager(QtGui.QWidget):
|
||||
return item.data(0, QtCore.Qt.UserRole).toInt()[0]
|
||||
else:
|
||||
return parentitem.data(0, QtCore.Qt.UserRole).toInt()[0]
|
||||
|
||||
def listRequest(self, message=None):
|
||||
data = []
|
||||
curindex, count = self.findServiceItem()
|
||||
if curindex >= 0 and curindex < len(self.serviceItems):
|
||||
curitem = self.serviceItems[curindex]
|
||||
else:
|
||||
curitem = None
|
||||
for item in self.serviceItems:
|
||||
service_item = item[u'service_item']
|
||||
data_item = {}
|
||||
data_item[u'title'] = unicode(service_item.title)
|
||||
data_item[u'plugin'] = unicode(service_item.name)
|
||||
data_item[u'notes'] = unicode(service_item.notes)
|
||||
data_item[u'selected'] = (item == curitem)
|
||||
data.append(data_item)
|
||||
Receiver.send_message(u'servicemanager_list_response', data)
|
@ -24,6 +24,7 @@
|
||||
###############################################################################
|
||||
|
||||
from PyQt4 import QtCore, QtGui
|
||||
from openlp.core.lib import translate
|
||||
|
||||
class Ui_ServiceNoteEdit(object):
|
||||
def setupUi(self, ServiceNoteEdit):
|
||||
@ -46,4 +47,4 @@ class Ui_ServiceNoteEdit(object):
|
||||
QtCore.QMetaObject.connectSlotsByName(ServiceNoteEdit)
|
||||
|
||||
def retranslateUi(self, ServiceNoteEdit):
|
||||
ServiceNoteEdit.setWindowTitle(self.trUtf8('Service Item Notes'))
|
||||
ServiceNoteEdit.setWindowTitle(translate('ServiceNoteForm', 'Service Item Notes'))
|
||||
|
@ -24,6 +24,7 @@
|
||||
###############################################################################
|
||||
|
||||
from PyQt4 import QtCore, QtGui
|
||||
from openlp.core.lib import translate
|
||||
|
||||
class Ui_SettingsDialog(object):
|
||||
def setupUi(self, SettingsDialog):
|
||||
@ -59,4 +60,4 @@ class Ui_SettingsDialog(object):
|
||||
QtCore.QMetaObject.connectSlotsByName(SettingsDialog)
|
||||
|
||||
def retranslateUi(self, SettingsDialog):
|
||||
SettingsDialog.setWindowTitle(self.trUtf8('Settings'))
|
||||
SettingsDialog.setWindowTitle(translate('SettingsForm', 'Settings'))
|
||||
|
@ -27,22 +27,25 @@ import logging
|
||||
|
||||
from PyQt4 import QtGui
|
||||
|
||||
from openlp.core.ui import GeneralTab, ThemesTab
|
||||
from openlp.core.ui import GeneralTab, ThemesTab, DisplayTab
|
||||
from settingsdialog import Ui_SettingsDialog
|
||||
|
||||
log = logging.getLogger(__name__)
|
||||
|
||||
class SettingsForm(QtGui.QDialog, Ui_SettingsDialog):
|
||||
|
||||
def __init__(self, screen_list, mainWindow, parent=None):
|
||||
def __init__(self, screens, mainWindow, parent=None):
|
||||
QtGui.QDialog.__init__(self, parent)
|
||||
self.setupUi(self)
|
||||
# General tab
|
||||
self.GeneralTab = GeneralTab(screen_list)
|
||||
self.GeneralTab = GeneralTab(screens)
|
||||
self.addTab(u'General', self.GeneralTab)
|
||||
# Themes tab
|
||||
self.ThemesTab = ThemesTab(mainWindow)
|
||||
self.addTab(u'Themes', self.ThemesTab)
|
||||
# Display tab
|
||||
self.DisplayTab = DisplayTab(screens)
|
||||
self.addTab(u'Display', self.DisplayTab)
|
||||
|
||||
def addTab(self, name, tab):
|
||||
log.info(u'Adding %s tab' % tab.tabTitle)
|
||||
|
@ -30,20 +30,30 @@ import os
|
||||
from PyQt4 import QtCore, QtGui
|
||||
from PyQt4.phonon import Phonon
|
||||
|
||||
class HideMode(object):
|
||||
"""
|
||||
This is basically an enumeration class which specifies the mode of a Bible.
|
||||
Mode refers to whether or not a Bible in OpenLP is a full Bible or needs to
|
||||
be downloaded from the Internet on an as-needed basis.
|
||||
"""
|
||||
Blank = 1
|
||||
Theme = 2
|
||||
|
||||
from openlp.core.lib import OpenLPToolbar, Receiver, str_to_bool, \
|
||||
PluginConfig, resize_image
|
||||
from openlp.core.ui import HideMode
|
||||
from openlp.core.lib import OpenLPToolbar, Receiver, resize_image, \
|
||||
ItemCapabilities
|
||||
|
||||
log = logging.getLogger(__name__)
|
||||
|
||||
class SlideThread(QtCore.QThread):
|
||||
"""
|
||||
A special Qt thread class to speed up the display of text based frames.
|
||||
This is threaded so it loads the frames in background
|
||||
"""
|
||||
def __init__(self, parent, prefix, count):
|
||||
QtCore.QThread.__init__(self, parent)
|
||||
self.prefix = prefix
|
||||
self.count = count
|
||||
|
||||
def run(self):
|
||||
"""
|
||||
Run the thread.
|
||||
"""
|
||||
time.sleep(1)
|
||||
for i in range(0, self.count):
|
||||
Receiver.send_message(u'%s_slide_cache' % self.prefix, i)
|
||||
|
||||
class SlideList(QtGui.QTableWidget):
|
||||
"""
|
||||
Customised version of QTableWidget which can respond to keyboard
|
||||
@ -52,11 +62,12 @@ class SlideList(QtGui.QTableWidget):
|
||||
def __init__(self, parent=None, name=None):
|
||||
QtGui.QTableWidget.__init__(self, parent.Controller)
|
||||
self.parent = parent
|
||||
self.hotkey_map = {QtCore.Qt.Key_Return: 'servicemanager_next_item',
|
||||
QtCore.Qt.Key_Space: 'live_slidecontroller_next_noloop',
|
||||
QtCore.Qt.Key_Enter: 'live_slidecontroller_next_noloop',
|
||||
QtCore.Qt.Key_0: 'servicemanager_next_item',
|
||||
QtCore.Qt.Key_Backspace: 'live_slidecontroller_previous_noloop'}
|
||||
self.hotkeyMap = {
|
||||
QtCore.Qt.Key_Return: 'servicemanager_next_item',
|
||||
QtCore.Qt.Key_Space: 'slidecontroller_live_next_noloop',
|
||||
QtCore.Qt.Key_Enter: 'slidecontroller_live_next_noloop',
|
||||
QtCore.Qt.Key_0: 'servicemanager_next_item',
|
||||
QtCore.Qt.Key_Backspace: 'slidecontroller_live_previous_noloop'}
|
||||
|
||||
def keyPressEvent(self, event):
|
||||
if type(event) == QtGui.QKeyEvent:
|
||||
@ -73,8 +84,8 @@ class SlideList(QtGui.QTableWidget):
|
||||
elif event.key() == QtCore.Qt.Key_PageDown:
|
||||
self.parent.onSlideSelectedLast()
|
||||
event.accept()
|
||||
elif event.key() in self.hotkey_map and self.parent.isLive:
|
||||
Receiver.send_message(self.hotkey_map[event.key()])
|
||||
elif event.key() in self.hotkeyMap and self.parent.isLive:
|
||||
Receiver.send_message(self.hotkeyMap[event.key()])
|
||||
event.accept()
|
||||
event.ignore()
|
||||
else:
|
||||
@ -93,20 +104,16 @@ class SlideController(QtGui.QWidget):
|
||||
self.settingsmanager = settingsmanager
|
||||
self.isLive = isLive
|
||||
self.parent = parent
|
||||
self.songsconfig = PluginConfig(u'Songs')
|
||||
self.image_list = [
|
||||
self.mainDisplay = self.parent.displayManager.mainDisplay
|
||||
self.loopList = [
|
||||
u'Start Loop',
|
||||
u'Stop Loop',
|
||||
u'Loop Separator',
|
||||
u'Image SpinBox'
|
||||
]
|
||||
self.song_edit_list = [
|
||||
self.songEditList = [
|
||||
u'Edit Song',
|
||||
]
|
||||
if isLive:
|
||||
self.labelWidth = 20
|
||||
else:
|
||||
self.labelWidth = 0
|
||||
self.timer_id = 0
|
||||
self.songEdit = False
|
||||
self.selectedRow = 0
|
||||
@ -122,11 +129,11 @@ class SlideController(QtGui.QWidget):
|
||||
if self.isLive:
|
||||
self.TypeLabel.setText(self.trUtf8('Live'))
|
||||
self.split = 1
|
||||
prefix = u'live_slidecontroller'
|
||||
self.typePrefix = u'live'
|
||||
else:
|
||||
self.TypeLabel.setText(self.trUtf8('Preview'))
|
||||
self.split = 0
|
||||
prefix = u'preview_slidecontroller'
|
||||
self.typePrefix = u'preview'
|
||||
self.TypeLabel.setStyleSheet(u'font-weight: bold; font-size: 12pt;')
|
||||
self.TypeLabel.setAlignment(QtCore.Qt.AlignCenter)
|
||||
self.PanelLayout.addWidget(self.TypeLabel)
|
||||
@ -146,17 +153,18 @@ class SlideController(QtGui.QWidget):
|
||||
self.ControllerLayout.setMargin(0)
|
||||
# Controller list view
|
||||
self.PreviewListWidget = SlideList(self)
|
||||
self.PreviewListWidget.setColumnCount(2)
|
||||
self.PreviewListWidget.setColumnCount(1)
|
||||
self.PreviewListWidget.horizontalHeader().setVisible(False)
|
||||
self.PreviewListWidget.verticalHeader().setVisible(False)
|
||||
self.PreviewListWidget.setColumnWidth(1, self.labelWidth)
|
||||
self.PreviewListWidget.setColumnWidth(1, self.Controller.width() - self.labelWidth)
|
||||
#self.PreviewListWidget.verticalHeader().setVisible(False)
|
||||
self.PreviewListWidget.setColumnWidth(
|
||||
0, self.Controller.width())
|
||||
self.PreviewListWidget.isLive = self.isLive
|
||||
self.PreviewListWidget.setObjectName(u'PreviewListWidget')
|
||||
self.PreviewListWidget.setSelectionBehavior(1)
|
||||
self.PreviewListWidget.setEditTriggers(
|
||||
QtGui.QAbstractItemView.NoEditTriggers)
|
||||
self.PreviewListWidget.setHorizontalScrollBarPolicy(QtCore.Qt.ScrollBarAlwaysOff)
|
||||
self.PreviewListWidget.setHorizontalScrollBarPolicy(
|
||||
QtCore.Qt.ScrollBarAlwaysOff)
|
||||
self.PreviewListWidget.setAlternatingRowColors(True)
|
||||
self.ControllerLayout.addWidget(self.PreviewListWidget)
|
||||
# Build the full toolbar
|
||||
@ -193,8 +201,6 @@ class SlideController(QtGui.QWidget):
|
||||
self.hideButton = self.Toolbar.addToolbarButton(
|
||||
u'Hide screen', u':/slides/slide_desktop.png',
|
||||
self.trUtf8('Hide Screen'), self.onHideDisplay, True)
|
||||
QtCore.QObject.connect(Receiver.get_receiver(),
|
||||
QtCore.SIGNAL(u'live_slide_blank'), self.blankScreen)
|
||||
if not self.isLive:
|
||||
self.Toolbar.addToolbarSeparator(u'Close Separator')
|
||||
self.Toolbar.addToolbarButton(
|
||||
@ -207,7 +213,7 @@ class SlideController(QtGui.QWidget):
|
||||
if isLive:
|
||||
self.Toolbar.addToolbarSeparator(u'Loop Separator')
|
||||
self.Toolbar.addToolbarButton(
|
||||
u'Start Loop', u':/media/media_time.png',
|
||||
u'Start Loop', u':/media/media_time.png',
|
||||
self.trUtf8('Start continuous loop'), self.onStartLoop)
|
||||
self.Toolbar.addToolbarButton(
|
||||
u'Stop Loop', u':/media/media_stop.png',
|
||||
@ -218,19 +224,36 @@ class SlideController(QtGui.QWidget):
|
||||
self.Toolbar.addToolbarWidget(
|
||||
u'Image SpinBox', self.DelaySpinBox)
|
||||
self.DelaySpinBox.setSuffix(self.trUtf8('s'))
|
||||
self.DelaySpinBox.setToolTip(self.trUtf8('Delay between slides in seconds'))
|
||||
self.DelaySpinBox.setToolTip(
|
||||
self.trUtf8('Delay between slides in seconds'))
|
||||
self.ControllerLayout.addWidget(self.Toolbar)
|
||||
#Build a Media ToolBar
|
||||
self.Mediabar = OpenLPToolbar(self)
|
||||
self.Mediabar.addToolbarButton(
|
||||
u'Media Start', u':/slides/media_playback_start.png',
|
||||
u'Media Start', u':/slides/media_playback_start.png',
|
||||
self.trUtf8('Start playing media'), self.onMediaPlay)
|
||||
self.Mediabar.addToolbarButton(
|
||||
u'Media Pause', u':/slides/media_playback_pause.png',
|
||||
u'Media Pause', u':/slides/media_playback_pause.png',
|
||||
self.trUtf8('Start playing media'), self.onMediaPause)
|
||||
self.Mediabar.addToolbarButton(
|
||||
u'Media Stop', u':/slides/media_playback_stop.png',
|
||||
u'Media Stop', u':/slides/media_playback_stop.png',
|
||||
self.trUtf8('Start playing media'), self.onMediaStop)
|
||||
if self.isLive:
|
||||
self.blankButton = self.Mediabar.addToolbarButton(
|
||||
u'Blank Screen', u':/slides/slide_blank.png',
|
||||
self.trUtf8('Blank Screen'), self.onBlankDisplay, True)
|
||||
self.themeButton = self.Mediabar.addToolbarButton(
|
||||
u'Display Theme', u':/slides/slide_theme.png',
|
||||
self.trUtf8('Theme Screen'), self.onThemeDisplay, True)
|
||||
self.hideButton = self.Mediabar.addToolbarButton(
|
||||
u'Hide screen', u':/slides/slide_desktop.png',
|
||||
self.trUtf8('Hide Screen'), self.onHideDisplay, True)
|
||||
if not self.isLive:
|
||||
self.seekSlider = Phonon.SeekSlider()
|
||||
self.seekSlider.setGeometry(QtCore.QRect(90, 260, 221, 24))
|
||||
self.seekSlider.setObjectName(u'seekSlider')
|
||||
self.Mediabar.addToolbarWidget(
|
||||
u'Seek Slider', self.seekSlider)
|
||||
self.volumeSlider = Phonon.VolumeSlider()
|
||||
self.volumeSlider.setGeometry(QtCore.QRect(90, 260, 221, 24))
|
||||
self.volumeSlider.setObjectName(u'volumeSlider')
|
||||
@ -243,13 +266,15 @@ class SlideController(QtGui.QWidget):
|
||||
self.SongMenu.setText(self.trUtf8('Go to Verse'))
|
||||
self.SongMenu.setPopupMode(QtGui.QToolButton.InstantPopup)
|
||||
self.Toolbar.addToolbarWidget(u'Song Menu', self.SongMenu)
|
||||
self.SongMenu.setMenu(QtGui.QMenu(self.trUtf8('Go to Verse'), self.Toolbar))
|
||||
self.SongMenu.setMenu(QtGui.QMenu(self.trUtf8('Go to Verse'),
|
||||
self.Toolbar))
|
||||
self.Toolbar.makeWidgetsInvisible([u'Song Menu'])
|
||||
# Screen preview area
|
||||
self.PreviewFrame = QtGui.QFrame(self.Splitter)
|
||||
self.PreviewFrame.setGeometry(QtCore.QRect(0, 0, 300, 225))
|
||||
self.PreviewFrame.setSizePolicy(QtGui.QSizePolicy(
|
||||
QtGui.QSizePolicy.Preferred, QtGui.QSizePolicy.Minimum, QtGui.QSizePolicy.Label))
|
||||
QtGui.QSizePolicy.Preferred, QtGui.QSizePolicy.Minimum,
|
||||
QtGui.QSizePolicy.Label))
|
||||
self.PreviewFrame.setFrameShape(QtGui.QFrame.StyledPanel)
|
||||
self.PreviewFrame.setFrameShadow(QtGui.QFrame.Sunken)
|
||||
self.PreviewFrame.setObjectName(u'PreviewFrame')
|
||||
@ -294,34 +319,56 @@ class SlideController(QtGui.QWidget):
|
||||
QtCore.SIGNAL(u'clicked(QModelIndex)'), self.onSlideSelected)
|
||||
if isLive:
|
||||
QtCore.QObject.connect(Receiver.get_receiver(),
|
||||
QtCore.SIGNAL(u'update_spin_delay'), self.receiveSpinDelay)
|
||||
Receiver.send_message(u'request_spin_delay')
|
||||
QtCore.SIGNAL(u'slidecontroller_live_spin_delay'),
|
||||
self.receiveSpinDelay)
|
||||
if isLive:
|
||||
self.Toolbar.makeWidgetsInvisible(self.image_list)
|
||||
self.Toolbar.makeWidgetsInvisible(self.loopList)
|
||||
else:
|
||||
self.Toolbar.makeWidgetsInvisible(self.song_edit_list)
|
||||
self.Toolbar.makeWidgetsInvisible(self.songEditList)
|
||||
self.Mediabar.setVisible(False)
|
||||
QtCore.QObject.connect(Receiver.get_receiver(),
|
||||
QtCore.SIGNAL(u'stop_display_loop'), self.onStopLoop)
|
||||
QtCore.SIGNAL(u'slidecontroller_%s_stop_loop' % self.typePrefix),
|
||||
self.onStopLoop)
|
||||
QtCore.QObject.connect(Receiver.get_receiver(),
|
||||
QtCore.SIGNAL(u'%s_first' % prefix), self.onSlideSelectedFirst)
|
||||
QtCore.SIGNAL(u'slidecontroller_%s_first' % self.typePrefix),
|
||||
self.onSlideSelectedFirst)
|
||||
QtCore.QObject.connect(Receiver.get_receiver(),
|
||||
QtCore.SIGNAL(u'%s_next' % prefix), self.onSlideSelectedNext)
|
||||
QtCore.SIGNAL(u'slidecontroller_%s_next' % self.typePrefix),
|
||||
self.onSlideSelectedNext)
|
||||
QtCore.QObject.connect(Receiver.get_receiver(),
|
||||
QtCore.SIGNAL(u'%s_previous' % prefix), self.onSlideSelectedPrevious)
|
||||
QtCore.SIGNAL(u'slidecontroller_%s_previous' % self.typePrefix),
|
||||
self.onSlideSelectedPrevious)
|
||||
QtCore.QObject.connect(Receiver.get_receiver(),
|
||||
QtCore.SIGNAL(u'%s_next_noloop' % prefix), self.onSlideSelectedNextNoloop)
|
||||
QtCore.SIGNAL(u'slidecontroller_%s_next_noloop' % self.typePrefix),
|
||||
self.onSlideSelectedNextNoloop)
|
||||
QtCore.QObject.connect(Receiver.get_receiver(),
|
||||
QtCore.SIGNAL(u'%s_previous_noloop' % prefix),
|
||||
QtCore.SIGNAL(u'slidecontroller_%s_previous_noloop' %
|
||||
self.typePrefix),
|
||||
self.onSlideSelectedPreviousNoloop)
|
||||
QtCore.QObject.connect(Receiver.get_receiver(),
|
||||
QtCore.SIGNAL(u'%s_last' % prefix), self.onSlideSelectedLast)
|
||||
QtCore.SIGNAL(u'slidecontroller_%s_last' % self.typePrefix),
|
||||
self.onSlideSelectedLast)
|
||||
QtCore.QObject.connect(Receiver.get_receiver(),
|
||||
QtCore.SIGNAL(u'%s_change' % prefix), self.onSlideChange)
|
||||
QtCore.SIGNAL(u'slidecontroller_%s_change' % self.typePrefix),
|
||||
self.onSlideChange)
|
||||
QtCore.QObject.connect(Receiver.get_receiver(),
|
||||
QtCore.SIGNAL(u'slidecontroller_%s_set' % self.typePrefix),
|
||||
self.onSlideSelectedIndex)
|
||||
QtCore.QObject.connect(Receiver.get_receiver(),
|
||||
QtCore.SIGNAL(u'slidecontroller_%s_blank' % self.typePrefix),
|
||||
self.onSlideBlank)
|
||||
QtCore.QObject.connect(Receiver.get_receiver(),
|
||||
QtCore.SIGNAL(u'slidecontroller_%s_unblank' % self.typePrefix),
|
||||
self.onSlideUnblank)
|
||||
QtCore.QObject.connect(Receiver.get_receiver(),
|
||||
QtCore.SIGNAL(u'slidecontroller_%s_text_request' % self.typePrefix),
|
||||
self.onTextRequest)
|
||||
QtCore.QObject.connect(self.Splitter,
|
||||
QtCore.SIGNAL(u'splitterMoved(int, int)'), self.trackSplitter)
|
||||
QtCore.QObject.connect(Receiver.get_receiver(),
|
||||
QtCore.SIGNAL(u'config_updated'), self.refreshServiceItem)
|
||||
QtCore.QObject.connect(Receiver.get_receiver(),
|
||||
QtCore.SIGNAL(u'%s_slide_cache' % self.typePrefix), self.slideCache)
|
||||
|
||||
def widthChanged(self):
|
||||
"""
|
||||
@ -330,8 +377,7 @@ class SlideController(QtGui.QWidget):
|
||||
"""
|
||||
width = self.parent.ControlSplitter.sizes()[self.split]
|
||||
height = width * self.parent.RenderManager.screen_ratio
|
||||
self.PreviewListWidget.setColumnWidth(0, self.labelWidth)
|
||||
self.PreviewListWidget.setColumnWidth(1, width - self.labelWidth)
|
||||
self.PreviewListWidget.setColumnWidth(0, width)
|
||||
#Sort out image hights (Songs , bibles excluded)
|
||||
if self.serviceItem and not self.serviceItem.is_text():
|
||||
for framenumber, frame in enumerate(self.serviceItem.get_frames()):
|
||||
@ -372,21 +418,20 @@ class SlideController(QtGui.QWidget):
|
||||
self.Toolbar.setVisible(True)
|
||||
self.Mediabar.setVisible(False)
|
||||
self.Toolbar.makeWidgetsInvisible([u'Song Menu'])
|
||||
self.Toolbar.makeWidgetsInvisible(self.image_list)
|
||||
self.Toolbar.makeWidgetsInvisible(self.loopList)
|
||||
if item.is_text():
|
||||
self.Toolbar.makeWidgetsInvisible(self.image_list)
|
||||
if item.is_song() and \
|
||||
str_to_bool(self.songsconfig.get_config(u'show songbar', True)) \
|
||||
and len(self.slideList) > 0:
|
||||
self.Toolbar.makeWidgetsInvisible(self.loopList)
|
||||
if QtCore.QSettings().value(
|
||||
self.parent.songsSettingsSection + u'/show songbar',
|
||||
QtCore.QVariant(True)).toBool() and len(self.slideList) > 0:
|
||||
self.Toolbar.makeWidgetsVisible([u'Song Menu'])
|
||||
elif item.is_image():
|
||||
#Not sensible to allow loops with 1 frame
|
||||
if len(item.get_frames()) > 1:
|
||||
self.Toolbar.makeWidgetsVisible(self.image_list)
|
||||
elif item.is_media():
|
||||
if item.is_capable(ItemCapabilities.AllowsLoop) and \
|
||||
len(item.get_frames()) > 1:
|
||||
self.Toolbar.makeWidgetsVisible(self.loopList)
|
||||
if item.is_media():
|
||||
self.Toolbar.setVisible(False)
|
||||
self.Mediabar.setVisible(True)
|
||||
self.volumeSlider.setAudioOutput(self.parent.mainDisplay.audio)
|
||||
#self.volumeSlider.setAudioOutput(self.mainDisplay.videoDisplay.audio)
|
||||
|
||||
def enablePreviewToolBar(self, item):
|
||||
"""
|
||||
@ -394,9 +439,9 @@ class SlideController(QtGui.QWidget):
|
||||
"""
|
||||
self.Toolbar.setVisible(True)
|
||||
self.Mediabar.setVisible(False)
|
||||
self.Toolbar.makeWidgetsInvisible(self.song_edit_list)
|
||||
if item.edit_enabled and item.from_plugin:
|
||||
self.Toolbar.makeWidgetsVisible(self.song_edit_list)
|
||||
self.Toolbar.makeWidgetsInvisible(self.songEditList)
|
||||
if item.is_capable(ItemCapabilities.AllowsEdit) and item.from_plugin:
|
||||
self.Toolbar.makeWidgetsVisible(self.songEditList)
|
||||
elif item.is_media():
|
||||
self.Toolbar.setVisible(False)
|
||||
self.Mediabar.setVisible(True)
|
||||
@ -454,20 +499,19 @@ class SlideController(QtGui.QWidget):
|
||||
Loads a ServiceItem into the system from ServiceManager
|
||||
Display the slide number passed
|
||||
"""
|
||||
log.debug(u'processsManagerItem')
|
||||
log.debug(u'processManagerItem')
|
||||
self.onStopLoop()
|
||||
#If old item was a command tell it to stop
|
||||
if self.serviceItem and self.serviceItem.is_command():
|
||||
self.onMediaStop()
|
||||
if serviceItem.is_media():
|
||||
self.onMediaStart(serviceItem)
|
||||
elif serviceItem.is_command():
|
||||
if self.isLive:
|
||||
blanked = self.blankButton.isChecked()
|
||||
else:
|
||||
blanked = False
|
||||
Receiver.send_message(u'%s_start' % serviceItem.name.lower(), \
|
||||
[serviceItem.title, serviceItem.get_frame_path(),
|
||||
serviceItem.get_frame_title(), slideno, self.isLive, blanked])
|
||||
if self.isLive:
|
||||
blanked = self.blankButton.isChecked()
|
||||
else:
|
||||
blanked = False
|
||||
Receiver.send_message(u'%s_start' % serviceItem.name.lower(),
|
||||
[serviceItem, self.isLive, blanked, slideno])
|
||||
self.slideList = {}
|
||||
width = self.parent.ControlSplitter.sizes()[self.split]
|
||||
#Set pointing cursor when we have somthing to point at
|
||||
@ -476,34 +520,37 @@ class SlideController(QtGui.QWidget):
|
||||
self.serviceItem = serviceItem
|
||||
self.PreviewListWidget.clear()
|
||||
self.PreviewListWidget.setRowCount(0)
|
||||
self.PreviewListWidget.setColumnWidth(0, self.labelWidth)
|
||||
self.PreviewListWidget.setColumnWidth(1, width - self.labelWidth)
|
||||
self.PreviewListWidget.setColumnWidth(0, width)
|
||||
if self.isLive:
|
||||
self.SongMenu.menu().clear()
|
||||
row = 0
|
||||
text = []
|
||||
for framenumber, frame in enumerate(self.serviceItem.get_frames()):
|
||||
self.PreviewListWidget.setRowCount(
|
||||
self.PreviewListWidget.rowCount() + 1)
|
||||
rowitem = QtGui.QTableWidgetItem()
|
||||
item = QtGui.QTableWidgetItem()
|
||||
slide_height = 0
|
||||
slideHeight = 0
|
||||
#It is a based Text Render
|
||||
if self.serviceItem.is_text():
|
||||
if self.isLive and frame[u'verseTag'] is not None:
|
||||
if frame[u'verseTag'] is not None:
|
||||
#only load the slot once
|
||||
bits = frame[u'verseTag'].split(u':')
|
||||
tag = None
|
||||
#If verse handle verse number else tag only
|
||||
if bits[0] == self.trUtf8('Verse'):
|
||||
tag = u'%s%s' % (bits[0][0], bits[1][0:] )
|
||||
row = bits[1][0:]
|
||||
if bits[0] == self.trUtf8('Verse') or \
|
||||
bits[0] == self.trUtf8('Chorus'):
|
||||
tag = u'%s\n%s' % (bits[0][0], bits[1][0:] )
|
||||
tag1 = u'%s%s' % (bits[0][0], bits[1][0:] )
|
||||
row = tag
|
||||
else:
|
||||
tag = bits[0]
|
||||
tag1 = tag
|
||||
row = bits[0][0:1]
|
||||
if tag not in self.slideList:
|
||||
self.slideList[tag] = framenumber
|
||||
self.SongMenu.menu().addAction(self.trUtf8(u'%s'%tag),
|
||||
self.onSongBarHandler)
|
||||
if self.isLive:
|
||||
if tag1 not in self.slideList:
|
||||
self.slideList[tag1] = framenumber
|
||||
self.SongMenu.menu().addAction(self.trUtf8(u'%s'%tag1),
|
||||
self.onSongBarHandler)
|
||||
else:
|
||||
row += 1
|
||||
item.setText(frame[u'text'])
|
||||
@ -515,19 +562,18 @@ class SlideController(QtGui.QWidget):
|
||||
self.parent.RenderManager.height)
|
||||
label.setScaledContents(True)
|
||||
label.setPixmap(QtGui.QPixmap.fromImage(pixmap))
|
||||
self.PreviewListWidget.setCellWidget(framenumber, 1, label)
|
||||
slide_height = width * self.parent.RenderManager.screen_ratio
|
||||
self.PreviewListWidget.setCellWidget(framenumber, 0, label)
|
||||
slideHeight = width * self.parent.RenderManager.screen_ratio
|
||||
row += 1
|
||||
rowitem.setText(unicode(row))
|
||||
self.PreviewListWidget.setItem(framenumber, 0, rowitem)
|
||||
self.PreviewListWidget.setItem(framenumber, 1, item)
|
||||
if slide_height != 0:
|
||||
self.PreviewListWidget.setRowHeight(framenumber, slide_height)
|
||||
text.append(unicode(row))
|
||||
self.PreviewListWidget.setItem(framenumber, 0, item)
|
||||
if slideHeight != 0:
|
||||
self.PreviewListWidget.setRowHeight(framenumber, slideHeight)
|
||||
self.PreviewListWidget.setVerticalHeaderLabels(text)
|
||||
if self.serviceItem.is_text():
|
||||
self.PreviewListWidget.resizeRowsToContents()
|
||||
self.PreviewListWidget.setColumnWidth(0, self.labelWidth)
|
||||
self.PreviewListWidget.setColumnWidth(1,
|
||||
self.PreviewListWidget.viewport().size().width() - self.labelWidth )
|
||||
self.PreviewListWidget.setColumnWidth(0,
|
||||
self.PreviewListWidget.viewport().size().width())
|
||||
if slideno > self.PreviewListWidget.rowCount():
|
||||
self.PreviewListWidget.selectRow(self.PreviewListWidget.rowCount())
|
||||
else:
|
||||
@ -535,9 +581,33 @@ class SlideController(QtGui.QWidget):
|
||||
self.enableToolBar(serviceItem)
|
||||
self.onSlideSelected()
|
||||
self.PreviewListWidget.setFocus()
|
||||
Receiver.send_message(u'slidecontroller_%s_started' % self.typePrefix,
|
||||
[serviceItem])
|
||||
if self.serviceItem.is_text():
|
||||
st = SlideThread(
|
||||
self, self.typePrefix, len(self.serviceItem.get_frames()))
|
||||
st.start()
|
||||
log.log(15, u'Display Rendering took %4s' % (time.time() - before))
|
||||
if self.isLive:
|
||||
self.serviceItem.request_audit()
|
||||
|
||||
def onTextRequest(self):
|
||||
"""
|
||||
Return the text for the current item in controller
|
||||
"""
|
||||
data = []
|
||||
if self.serviceItem:
|
||||
for framenumber, frame in enumerate(self.serviceItem.get_frames()):
|
||||
dataItem = {}
|
||||
if self.serviceItem.is_text():
|
||||
dataItem[u'tag'] = unicode(frame[u'verseTag'])
|
||||
dataItem[u'text'] = unicode(frame[u'text'])
|
||||
else:
|
||||
dataItem[u'tag'] = unicode(framenumber)
|
||||
dataItem[u'text'] = u''
|
||||
dataItem[u'selected'] = \
|
||||
(self.PreviewListWidget.currentRow() == framenumber)
|
||||
data.append(dataItem)
|
||||
Receiver.send_message(u'slidecontroller_%s_text_response'
|
||||
% self.typePrefix, data)
|
||||
|
||||
#Screen event methods
|
||||
def onSlideSelectedFirst(self):
|
||||
@ -546,60 +616,120 @@ class SlideController(QtGui.QWidget):
|
||||
"""
|
||||
if not self.serviceItem:
|
||||
return
|
||||
Receiver.send_message(u'%s_first' % self.serviceItem.name.lower(),
|
||||
[self.serviceItem, self.isLive])
|
||||
if self.serviceItem.is_command():
|
||||
Receiver.send_message(u'%s_first'% \
|
||||
self.serviceItem.name.lower(), self.isLive)
|
||||
self.updatePreview()
|
||||
else:
|
||||
self.PreviewListWidget.selectRow(0)
|
||||
self.onSlideSelected()
|
||||
|
||||
def onBlankDisplay(self, force=False):
|
||||
def onSlideSelectedIndex(self, message):
|
||||
"""
|
||||
Go to the requested slide
|
||||
"""
|
||||
index = int(message[0])
|
||||
if not self.serviceItem:
|
||||
return
|
||||
Receiver.send_message(u'%s_slide' % self.serviceItem.name.lower(),
|
||||
[self.serviceItem, self.isLive, index])
|
||||
if self.serviceItem.is_command():
|
||||
self.updatePreview()
|
||||
else:
|
||||
self.PreviewListWidget.selectRow(index)
|
||||
self.onSlideSelected()
|
||||
|
||||
def onSlideBlank(self):
|
||||
"""
|
||||
Handle the slidecontroller blank event
|
||||
"""
|
||||
self.onBlankDisplay(True)
|
||||
|
||||
def onSlideUnblank(self):
|
||||
"""
|
||||
Handle the slidecontroller unblank event
|
||||
"""
|
||||
self.onBlankDisplay(False)
|
||||
|
||||
def onBlankDisplay(self, checked):
|
||||
"""
|
||||
Handle the blank screen button
|
||||
"""
|
||||
log.debug(u'onBlankDisplay %d' % force)
|
||||
if force:
|
||||
self.blankButton.setChecked(True)
|
||||
self.blankScreen(HideMode.Blank, self.blankButton.isChecked())
|
||||
self.parent.generalConfig.set_config(u'screen blank',
|
||||
self.blankButton.isChecked())
|
||||
log.debug(u'onBlankDisplay %d' % checked)
|
||||
self.hideButton.setChecked(False)
|
||||
self.themeButton.setChecked(False)
|
||||
QtCore.QSettings().setValue(
|
||||
self.parent.generalSettingsSection + u'/screen blank',
|
||||
QtCore.QVariant(checked))
|
||||
if checked:
|
||||
Receiver.send_message(u'maindisplay_hide', HideMode.Blank)
|
||||
self.blankPlugin(True)
|
||||
else:
|
||||
Receiver.send_message(u'maindisplay_show')
|
||||
self.blankPlugin(False)
|
||||
|
||||
def onThemeDisplay(self, force=False):
|
||||
def onThemeDisplay(self, checked):
|
||||
"""
|
||||
Handle the Theme screen button
|
||||
"""
|
||||
log.debug(u'onThemeDisplay %d' % force)
|
||||
if force:
|
||||
self.themeButton.setChecked(True)
|
||||
self.blankScreen(HideMode.Theme, self.themeButton.isChecked())
|
||||
log.debug(u'onThemeDisplay %d' % checked)
|
||||
self.blankButton.setChecked(False)
|
||||
self.hideButton.setChecked(False)
|
||||
if checked:
|
||||
Receiver.send_message(u'maindisplay_hide', HideMode.Theme)
|
||||
self.blankPlugin(True)
|
||||
else:
|
||||
Receiver.send_message(u'maindisplay_show')
|
||||
self.blankPlugin(False)
|
||||
|
||||
def onHideDisplay(self, force=False):
|
||||
def onHideDisplay(self, checked):
|
||||
"""
|
||||
Handle the Hide screen button
|
||||
"""
|
||||
log.debug(u'onHideDisplay %d' % force)
|
||||
if force:
|
||||
self.themeButton.setChecked(True)
|
||||
if self.hideButton.isChecked():
|
||||
self.parent.mainDisplay.hideDisplay()
|
||||
log.debug(u'onHideDisplay %d' % checked)
|
||||
self.blankButton.setChecked(False)
|
||||
self.themeButton.setChecked(False)
|
||||
if checked:
|
||||
Receiver.send_message(u'maindisplay_hide', HideMode.Screen)
|
||||
self.hidePlugin(True)
|
||||
else:
|
||||
self.parent.mainDisplay.showDisplay()
|
||||
Receiver.send_message(u'maindisplay_show')
|
||||
self.hidePlugin(False)
|
||||
|
||||
def blankScreen(self, blankType, blanked=False):
|
||||
def blankPlugin(self, blank):
|
||||
"""
|
||||
Blank the display screen.
|
||||
"""
|
||||
if self.serviceItem is not None:
|
||||
if self.serviceItem.is_command():
|
||||
if blanked:
|
||||
Receiver.send_message(u'%s_blank'% self.serviceItem.name.lower())
|
||||
else:
|
||||
Receiver.send_message(u'%s_unblank'% self.serviceItem.name.lower())
|
||||
if blank:
|
||||
Receiver.send_message(u'%s_blank'
|
||||
% self.serviceItem.name.lower(),
|
||||
[self.serviceItem, self.isLive])
|
||||
else:
|
||||
self.parent.mainDisplay.blankDisplay(blankType, blanked)
|
||||
else:
|
||||
self.parent.mainDisplay.blankDisplay(blankType, blanked)
|
||||
Receiver.send_message(u'%s_unblank'
|
||||
% self.serviceItem.name.lower(),
|
||||
[self.serviceItem, self.isLive])
|
||||
|
||||
def hidePlugin(self, hide):
|
||||
"""
|
||||
Blank the display screen.
|
||||
"""
|
||||
if self.serviceItem is not None:
|
||||
if hide:
|
||||
Receiver.send_message(u'%s_hide'
|
||||
% self.serviceItem.name.lower(),
|
||||
[self.serviceItem, self.isLive])
|
||||
else:
|
||||
Receiver.send_message(u'%s_unblank'
|
||||
% self.serviceItem.name.lower(),
|
||||
[self.serviceItem, self.isLive])
|
||||
|
||||
def slideCache(self, slide):
|
||||
"""
|
||||
Generate a slide cache item rendered and ready for use
|
||||
in the background.
|
||||
"""
|
||||
self.serviceItem.get_rendered_frame(int(slide))
|
||||
|
||||
def onSlideSelected(self):
|
||||
"""
|
||||
@ -609,9 +739,9 @@ class SlideController(QtGui.QWidget):
|
||||
row = self.PreviewListWidget.currentRow()
|
||||
self.selectedRow = 0
|
||||
if row > -1 and row < self.PreviewListWidget.rowCount():
|
||||
Receiver.send_message(u'%s_slide' % self.serviceItem.name.lower(),
|
||||
[self.serviceItem, self.isLive, row])
|
||||
if self.serviceItem.is_command() and self.isLive:
|
||||
Receiver.send_message(u'%s_slide'% \
|
||||
self.serviceItem.name.lower(), u'%s:%s' % (row, self.isLive))
|
||||
self.updatePreview()
|
||||
else:
|
||||
before = time.time()
|
||||
@ -620,13 +750,18 @@ class SlideController(QtGui.QWidget):
|
||||
self.SlidePreview.setPixmap(QtGui.QPixmap.fromImage(frame))
|
||||
else:
|
||||
if isinstance(frame[u'main'], basestring):
|
||||
self.SlidePreview.setPixmap(QtGui.QPixmap(frame[u'main']))
|
||||
self.SlidePreview.setPixmap(
|
||||
QtGui.QPixmap(frame[u'main']))
|
||||
else:
|
||||
self.SlidePreview.setPixmap(QtGui.QPixmap.fromImage(frame[u'main']))
|
||||
log.log(15, u'Slide Rendering took %4s' % (time.time() - before))
|
||||
self.SlidePreview.setPixmap(
|
||||
QtGui.QPixmap.fromImage(frame[u'main']))
|
||||
log.log(
|
||||
15, u'Slide Rendering took %4s' % (time.time() - before))
|
||||
if self.isLive:
|
||||
self.parent.mainDisplay.frameView(frame, True)
|
||||
self.mainDisplay.frameView(frame, True)
|
||||
self.selectedRow = row
|
||||
Receiver.send_message(u'slidecontroller_%s_changed' % self.typePrefix,
|
||||
row)
|
||||
|
||||
def onSlideChange(self, row):
|
||||
"""
|
||||
@ -634,6 +769,8 @@ class SlideController(QtGui.QWidget):
|
||||
"""
|
||||
self.PreviewListWidget.selectRow(row)
|
||||
self.updatePreview()
|
||||
Receiver.send_message(u'slidecontroller_%s_changed' % self.typePrefix,
|
||||
row)
|
||||
|
||||
def updatePreview(self):
|
||||
rm = self.parent.RenderManager
|
||||
@ -663,9 +800,9 @@ class SlideController(QtGui.QWidget):
|
||||
"""
|
||||
if not self.serviceItem:
|
||||
return
|
||||
Receiver.send_message(u'%s_next' % self.serviceItem.name.lower(),
|
||||
[self.serviceItem, self.isLive])
|
||||
if self.serviceItem.is_command():
|
||||
Receiver.send_message(u'%s_next' % \
|
||||
self.serviceItem.name.lower(), self.isLive)
|
||||
self.updatePreview()
|
||||
else:
|
||||
row = self.PreviewListWidget.currentRow() + 1
|
||||
@ -687,9 +824,9 @@ class SlideController(QtGui.QWidget):
|
||||
"""
|
||||
if not self.serviceItem:
|
||||
return
|
||||
Receiver.send_message(u'%s_previous' % self.serviceItem.name.lower(),
|
||||
[self.serviceItem, self.isLive])
|
||||
if self.serviceItem.is_command():
|
||||
Receiver.send_message(
|
||||
u'%s_previous'% self.serviceItem.name.lower(), self.isLive)
|
||||
self.updatePreview()
|
||||
else:
|
||||
row = self.PreviewListWidget.currentRow() - 1
|
||||
@ -707,9 +844,9 @@ class SlideController(QtGui.QWidget):
|
||||
"""
|
||||
if not self.serviceItem:
|
||||
return
|
||||
Receiver.send_message(u'%s_last' % self.serviceItem.name.lower(),
|
||||
[self.serviceItem, self.isLive])
|
||||
if self.serviceItem.is_command():
|
||||
Receiver.send_message(u'%s_last' % \
|
||||
self.serviceItem.name.lower(), self.isLive)
|
||||
self.updatePreview()
|
||||
else:
|
||||
self.PreviewListWidget.selectRow(
|
||||
@ -728,7 +865,9 @@ class SlideController(QtGui.QWidget):
|
||||
"""
|
||||
Stop the timer loop running
|
||||
"""
|
||||
self.killTimer(self.timer_id)
|
||||
if self.timer_id != 0:
|
||||
self.killTimer(self.timer_id)
|
||||
self.timer_id = 0
|
||||
|
||||
def timerEvent(self, event):
|
||||
"""
|
||||
@ -738,9 +877,12 @@ class SlideController(QtGui.QWidget):
|
||||
self.onSlideSelectedNext()
|
||||
|
||||
def onEditSong(self):
|
||||
"""
|
||||
From the preview display requires the service Item to be editied
|
||||
"""
|
||||
self.songEdit = True
|
||||
Receiver.send_message(u'%s_edit' % self.serviceItem.name, u'P:%s' %
|
||||
self.serviceItem.editId )
|
||||
Receiver.send_message(u'%s_edit' % self.serviceItem.name.lower(),
|
||||
u'P:%s' % self.serviceItem.editId)
|
||||
|
||||
def onGoLive(self):
|
||||
"""
|
||||
@ -752,34 +894,51 @@ class SlideController(QtGui.QWidget):
|
||||
self.serviceItem, row)
|
||||
|
||||
def onMediaStart(self, item):
|
||||
"""
|
||||
Respond to the arrival of a media service item
|
||||
"""
|
||||
log.debug(u'SlideController onMediaStart')
|
||||
if self.isLive:
|
||||
Receiver.send_message(u'%s_start' % item.name.lower(), \
|
||||
[item.title, item.get_frame_path(),
|
||||
item.get_frame_title(), self.isLive, self.blankButton.isChecked()])
|
||||
Receiver.send_message(u'videodisplay_start',
|
||||
[item, self.blankButton.isChecked()])
|
||||
else:
|
||||
self.mediaObject.stop()
|
||||
self.mediaObject.clearQueue()
|
||||
file = os.path.join(item.service_item_path, item.get_frame_title())
|
||||
file = os.path.join(item.get_frame_path(), item.get_frame_title())
|
||||
self.mediaObject.setCurrentSource(Phonon.MediaSource(file))
|
||||
self.seekSlider.setMediaObject(self.mediaObject)
|
||||
self.seekSlider.show()
|
||||
self.onMediaPlay()
|
||||
|
||||
def onMediaPause(self):
|
||||
"""
|
||||
Respond to the Pause from the media Toolbar
|
||||
"""
|
||||
log.debug(u'SlideController onMediaPause')
|
||||
if self.isLive:
|
||||
Receiver.send_message(u'%s_pause'% self.serviceItem.name.lower())
|
||||
Receiver.send_message(u'videodisplay_pause')
|
||||
else:
|
||||
self.mediaObject.pause()
|
||||
|
||||
def onMediaPlay(self):
|
||||
"""
|
||||
Respond to the Play from the media Toolbar
|
||||
"""
|
||||
log.debug(u'SlideController onMediaPlay')
|
||||
if self.isLive:
|
||||
Receiver.send_message(u'%s_play'% self.serviceItem.name.lower(), self.isLive)
|
||||
Receiver.send_message(u'videodisplay_play')
|
||||
else:
|
||||
self.SlidePreview.hide()
|
||||
self.video.show()
|
||||
self.mediaObject.play()
|
||||
|
||||
def onMediaStop(self):
|
||||
"""
|
||||
Respond to the Stop from the media Toolbar
|
||||
"""
|
||||
log.debug(u'SlideController onMediaStop')
|
||||
if self.isLive:
|
||||
Receiver.send_message(u'%s_stop'% self.serviceItem.name.lower(), self.isLive)
|
||||
Receiver.send_message(u'videodisplay_stop')
|
||||
else:
|
||||
self.mediaObject.stop()
|
||||
self.video.hide()
|
||||
|
@ -1,160 +0,0 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
# vim: autoindent shiftwidth=4 expandtab textwidth=80 tabstop=4 softtabstop=4
|
||||
|
||||
###############################################################################
|
||||
# OpenLP - Open Source Lyrics Projection #
|
||||
# --------------------------------------------------------------------------- #
|
||||
# Copyright (c) 2008-2010 Raoul Snyman #
|
||||
# Portions copyright (c) 2008-2010 Tim Bentley, Jonathan Corwin, Michael #
|
||||
# Gorven, Scott Guerrieri, Christian Richter, Maikel Stuivenberg, Martin #
|
||||
# Thompson, Jon Tibble, Carsten Tinggaard #
|
||||
# --------------------------------------------------------------------------- #
|
||||
# This program is free software; you can redistribute it and/or modify it #
|
||||
# under the terms of the GNU General Public License as published by the Free #
|
||||
# Software Foundation; version 2 of the License. #
|
||||
# #
|
||||
# This program is distributed in the hope that it will be useful, but WITHOUT #
|
||||
# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or #
|
||||
# FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for #
|
||||
# more details. #
|
||||
# #
|
||||
# You should have received a copy of the GNU General Public License along #
|
||||
# with this program; if not, write to the Free Software Foundation, Inc., 59 #
|
||||
# Temple Place, Suite 330, Boston, MA 02111-1307 USA #
|
||||
###############################################################################
|
||||
|
||||
import sys
|
||||
import os
|
||||
import os.path
|
||||
import logging
|
||||
|
||||
from PyQt4 import QtGui
|
||||
|
||||
from openlp.core.ui import ServiceManager
|
||||
from openlp.plugins.images.lib import ImageServiceItem
|
||||
|
||||
mypath = os.path.split(os.path.abspath(__file__))[0]
|
||||
sys.path.insert(0, (os.path.join(mypath, '..', '..', '..', '..')))
|
||||
|
||||
logging.basicConfig(filename='test_service_manager.log', level=logging.INFO,
|
||||
filemode='w')
|
||||
|
||||
# # from http://aspn.activestate.com/ASPN/Cookbook/Python/Recipe/66062
|
||||
# def whoami(depth=1):
|
||||
# return sys._getframe(depth).f_code.co_name
|
||||
global app
|
||||
global log
|
||||
log = logging.getLogger(u'TestServiceManager')
|
||||
|
||||
class TestServiceManager_base:
|
||||
def __init__(self):
|
||||
pass
|
||||
|
||||
def setup_class(self):
|
||||
log.info( "class setup" + unicode(self))
|
||||
try:
|
||||
if app is None:
|
||||
app = QtGui.QApplication([])
|
||||
except UnboundLocalError:
|
||||
app = QtGui.QApplication([])
|
||||
|
||||
def teardown_class(self):
|
||||
pass
|
||||
|
||||
def setup_method(self, method):
|
||||
log.info(u'Setup method:' + unicode(method))
|
||||
self.expected_answer = "Don't know yet"
|
||||
self.answer = None
|
||||
self.s = ServiceManager(None)
|
||||
log.info(u'--------------- Setup Done -------------')
|
||||
|
||||
def teardown_method(self, method):
|
||||
self.s = None
|
||||
|
||||
def select_row(self, row):
|
||||
# now select the line we just added
|
||||
# first get the index
|
||||
i = QModelIndex(self.s.service_data.index(0,0))
|
||||
# make a selection of it
|
||||
self.sm = QItemSelectionModel(self.s.service_data)
|
||||
self.sm.select(i, QItemSelectionModel.ClearAndSelect)
|
||||
log.info(unicode(self.sm.selectedIndexes()))
|
||||
self.s.TreeView.setSelectionModel(self.sm)
|
||||
log.info(u'Selected indexes = ' + unicode(
|
||||
self.s.TreeView.selectedIndexes()))
|
||||
|
||||
def test_easy(self):
|
||||
log.info(u'test_easy')
|
||||
item = ImageServiceItem(None)
|
||||
item.add(u'test.gif')
|
||||
self.s.addServiceItem(item)
|
||||
answer = self.s.service_as_text()
|
||||
log.info(u'Answer = ' + unicode(answer))
|
||||
lines = answer.split(u'\n')
|
||||
log.info(u'lines = ' + unicode(lines))
|
||||
assert lines[0].startswith(u'# <openlp.plugins.images.imageserviceitem.ImageServiceItem object')
|
||||
assert lines[1] == "test.gif"
|
||||
log.info(u'done')
|
||||
|
||||
def test_2items_as_separate_items(self):
|
||||
# If nothing is selected when item is added, a new base service item
|
||||
# is added
|
||||
log.info(u'test_2items_as_separate_items')
|
||||
item = ImageServiceItem(None)
|
||||
item.add(u'test.gif')
|
||||
self.s.addServiceItem(item)
|
||||
item = ImageServiceItem(None)
|
||||
item.add(u'test2.gif')
|
||||
item.add(u'test3.gif')
|
||||
self.s.addServiceItem(item)
|
||||
answer = self.s.service_as_text()
|
||||
log.info(u'Answer = ' + unicode(answer))
|
||||
lines = answer.split(u'\n')
|
||||
log.info(u'lines = ' + unicode(lines))
|
||||
assert lines[0].startswith(u'# <openlp.plugins.images.imageserviceitem.ImageServiceItem object')
|
||||
assert lines[1] == "test.gif"
|
||||
assert lines[2].startswith(u'# <openlp.plugins.images.imageserviceitem.ImageServiceItem object')
|
||||
assert lines[3] == "test2.gif"
|
||||
assert lines[4] == "test3.gif"
|
||||
log.info(u'done')
|
||||
|
||||
def test_2items_merged(self):
|
||||
# If the first object is selected when item is added it should be
|
||||
# extended
|
||||
log.info(u'test_2items_merged')
|
||||
item = ImageServiceItem(None)
|
||||
item.add(u'test.gif')
|
||||
self.s.addServiceItem(item)
|
||||
self.select_row(0)
|
||||
log.info(u'Selected indexes = ' + unicode(
|
||||
self.s.TreeView.selectedIndexes()))
|
||||
item = ImageServiceItem(None)
|
||||
item.add(u'test2.gif')
|
||||
item.add(u'test3.gif')
|
||||
self.s.addServiceItem(item)
|
||||
answer = self.s.service_as_text()
|
||||
log.info(u'Answer = ' + unicode(answer))
|
||||
lines = answer.split(u'\n')
|
||||
log.info(u'lines = ' + unicode(lines))
|
||||
assert lines[0].startswith(u'# <openlp.plugins.images.imageserviceitem.ImageServiceItem object')
|
||||
assert lines[1] == "test.gif"
|
||||
assert lines[2] == "test2.gif"
|
||||
assert lines[3] == "test3.gif"
|
||||
log.info(u'done')
|
||||
|
||||
# more tests to do:
|
||||
# add different types of service item
|
||||
# move up, down
|
||||
# move to top, bottom
|
||||
# new and save as
|
||||
# deleting items
|
||||
|
||||
|
||||
if __name__ == "__main__":
|
||||
t=TestServiceManager_base()
|
||||
t.setup_class()
|
||||
t.setup_method(None)
|
||||
t.test_easy()
|
||||
t.teardown_method(None)
|
||||
print "Pass"
|
||||
log.info(u'Pass')
|
@ -33,10 +33,10 @@ from PyQt4 import QtCore, QtGui
|
||||
|
||||
from openlp.core.ui import AmendThemeForm
|
||||
from openlp.core.theme import Theme
|
||||
from openlp.core.lib import PluginConfig, OpenLPToolbar, contextMenuAction, \
|
||||
from openlp.core.lib import OpenLPToolbar, contextMenuAction, \
|
||||
ThemeXML, str_to_bool, get_text_file_string, build_icon, Receiver, \
|
||||
contextMenuSeparator
|
||||
from openlp.core.utils import ConfigHelper
|
||||
contextMenuSeparator, SettingsManager
|
||||
from openlp.core.utils import AppLocation
|
||||
|
||||
log = logging.getLogger(__name__)
|
||||
|
||||
@ -47,6 +47,7 @@ class ThemeManager(QtGui.QWidget):
|
||||
def __init__(self, parent):
|
||||
QtGui.QWidget.__init__(self, parent)
|
||||
self.parent = parent
|
||||
self.settingsSection = u'themes'
|
||||
self.Layout = QtGui.QVBoxLayout(self)
|
||||
self.Layout.setSpacing(0)
|
||||
self.Layout.setMargin(0)
|
||||
@ -102,19 +103,18 @@ class ThemeManager(QtGui.QWidget):
|
||||
QtCore.SIGNAL(u'doubleClicked(QModelIndex)'),
|
||||
self.changeGlobalFromScreen)
|
||||
QtCore.QObject.connect(Receiver.get_receiver(),
|
||||
QtCore.SIGNAL(u'update_global_theme'), self.changeGlobalFromTab)
|
||||
QtCore.SIGNAL(u'theme_update_global'), self.changeGlobalFromTab)
|
||||
#Variables
|
||||
self.themelist = []
|
||||
self.path = os.path.join(ConfigHelper.get_data_path(), u'themes')
|
||||
self.path = AppLocation.get_section_data_path(self.settingsSection)
|
||||
self.checkThemesExists(self.path)
|
||||
self.thumbPath = os.path.join(self.path, u'.thumbnails')
|
||||
self.thumbPath = os.path.join(self.path, u'thumbnails')
|
||||
self.checkThemesExists(self.thumbPath)
|
||||
self.amendThemeForm.path = self.path
|
||||
# Last little bits of setting up
|
||||
self.config = PluginConfig(u'themes')
|
||||
self.servicePath = self.config.get_data_path()
|
||||
self.global_theme = unicode(
|
||||
self.config.get_config(u'global theme', u''))
|
||||
self.global_theme = unicode(QtCore.QSettings().value(
|
||||
self.settingsSection + u'/global theme',
|
||||
QtCore.QVariant(u'')).toString())
|
||||
|
||||
def changeGlobalFromTab(self, themeName):
|
||||
log.debug(u'changeGlobalFromTab %s', themeName)
|
||||
@ -146,9 +146,10 @@ class ThemeManager(QtGui.QWidget):
|
||||
self.ThemeListWidget.item(count).text())
|
||||
name = u'%s (%s)' % (self.global_theme, self.trUtf8('default'))
|
||||
self.ThemeListWidget.item(count).setText(name)
|
||||
self.config.set_config(u'global theme', self.global_theme)
|
||||
Receiver.send_message(
|
||||
u'update_global_theme', self.global_theme)
|
||||
QtCore.QSettings().setValue(
|
||||
self.settingsSection + u'/global theme',
|
||||
QtCore.QVariant(self.global_theme))
|
||||
Receiver.send_message(u'theme_update_global', self.global_theme)
|
||||
self.pushThemes()
|
||||
|
||||
def onAddTheme(self):
|
||||
@ -168,8 +169,9 @@ class ThemeManager(QtGui.QWidget):
|
||||
self.amendThemeForm.exec_()
|
||||
|
||||
def onDeleteTheme(self):
|
||||
self.global_theme = unicode(
|
||||
self.config.get_config(u'global theme', u''))
|
||||
self.global_theme = unicode(QtCore.QSettings().value(
|
||||
self.settingsSection + u'/global theme',
|
||||
QtCore.QVariant(u'')).toString())
|
||||
item = self.ThemeListWidget.currentItem()
|
||||
if item:
|
||||
theme = unicode(item.text())
|
||||
@ -222,10 +224,10 @@ class ThemeManager(QtGui.QWidget):
|
||||
theme = unicode(item.data(QtCore.Qt.UserRole).toString())
|
||||
path = QtGui.QFileDialog.getExistingDirectory(self,
|
||||
unicode(self.trUtf8('Save Theme - (%s)')) % theme,
|
||||
self.config.get_last_dir(1) )
|
||||
SettingsManager.get_last_dir(self.settingsSection, 1))
|
||||
path = unicode(path)
|
||||
if path:
|
||||
self.config.set_last_dir(path, 1)
|
||||
SettingsManager.set_last_dir(self.settingsSection, path, 1)
|
||||
themePath = os.path.join(path, theme + u'.theme')
|
||||
zip = None
|
||||
try:
|
||||
@ -234,7 +236,8 @@ class ThemeManager(QtGui.QWidget):
|
||||
for root, dirs, files in os.walk(source):
|
||||
for name in files:
|
||||
zip.write(
|
||||
os.path.join(source, name), os.path.join(theme, name))
|
||||
os.path.join(source, name),
|
||||
os.path.join(theme, name))
|
||||
except:
|
||||
log.exception(u'Export Theme Failed')
|
||||
finally:
|
||||
@ -244,11 +247,12 @@ class ThemeManager(QtGui.QWidget):
|
||||
def onImportTheme(self):
|
||||
files = QtGui.QFileDialog.getOpenFileNames(
|
||||
self, self.trUtf8('Select Theme Import File'),
|
||||
self.config.get_last_dir(), u'Theme (*.*)')
|
||||
SettingsManager.get_last_dir(self.settingsSection), u'Theme (*.*)')
|
||||
log.info(u'New Themes %s', unicode(files))
|
||||
if files:
|
||||
for file in files:
|
||||
self.config.set_last_dir(unicode(file))
|
||||
SettingsManager.set_last_dir(
|
||||
self.settingsSection, unicode(file))
|
||||
self.unzipTheme(file, self.path)
|
||||
self.loadThemes()
|
||||
|
||||
@ -291,7 +295,7 @@ class ThemeManager(QtGui.QWidget):
|
||||
self.pushThemes()
|
||||
|
||||
def pushThemes(self):
|
||||
Receiver.send_message(u'update_themes', self.getThemes() )
|
||||
Receiver.send_message(u'theme_update_list', self.getThemes())
|
||||
|
||||
def getThemes(self):
|
||||
return self.themelist
|
||||
|
@ -103,7 +103,7 @@ class ThemesTab(SettingsTab):
|
||||
QtCore.QObject.connect(self.DefaultComboBox,
|
||||
QtCore.SIGNAL(u'activated(int)'), self.onDefaultComboBoxChanged)
|
||||
QtCore.QObject.connect(Receiver.get_receiver(),
|
||||
QtCore.SIGNAL(u'update_themes'), self.updateThemeList)
|
||||
QtCore.SIGNAL(u'theme_update_list'), self.updateThemeList)
|
||||
|
||||
def retranslateUi(self):
|
||||
self.GlobalGroupBox.setTitle(self.trUtf8('Global theme'))
|
||||
@ -123,9 +123,13 @@ class ThemesTab(SettingsTab):
|
||||
'songs.'))
|
||||
|
||||
def load(self):
|
||||
self.theme_level = int(self.config.get_config(u'theme level',
|
||||
ThemeLevel.Global))
|
||||
self.global_theme = self.config.get_config(u'global theme', u'')
|
||||
settings = QtCore.QSettings()
|
||||
settings.beginGroup(self.settingsSection)
|
||||
self.theme_level = settings.value(
|
||||
u'theme level', QtCore.QVariant(ThemeLevel.Global)).toInt()[0]
|
||||
self.global_theme = unicode(settings.value(
|
||||
u'global theme', QtCore.QVariant(u'')).toString())
|
||||
settings.endGroup()
|
||||
if self.theme_level == ThemeLevel.Global:
|
||||
self.GlobalLevelRadioButton.setChecked(True)
|
||||
elif self.theme_level == ThemeLevel.Service:
|
||||
@ -134,14 +138,19 @@ class ThemesTab(SettingsTab):
|
||||
self.SongLevelRadioButton.setChecked(True)
|
||||
|
||||
def save(self):
|
||||
self.config.set_config(u'theme level', self.theme_level)
|
||||
self.config.set_config(u'global theme',self.global_theme)
|
||||
Receiver.send_message(u'update_global_theme', self.global_theme)
|
||||
settings = QtCore.QSettings()
|
||||
settings.beginGroup(self.settingsSection)
|
||||
settings.setValue(u'theme level',
|
||||
QtCore.QVariant(self.theme_level))
|
||||
settings.setValue(u'global theme',
|
||||
QtCore.QVariant(self.global_theme))
|
||||
settings.endGroup()
|
||||
Receiver.send_message(u'theme_update_global', self.global_theme)
|
||||
self.parent.RenderManager.set_global_theme(
|
||||
self.global_theme, self.theme_level)
|
||||
|
||||
def postSetUp(self):
|
||||
Receiver.send_message(u'update_global_theme', self.global_theme)
|
||||
Receiver.send_message(u'theme_update_global', self.global_theme)
|
||||
|
||||
def onSongLevelButtonPressed(self):
|
||||
self.theme_level = ThemeLevel.Song
|
||||
@ -169,7 +178,9 @@ class ThemesTab(SettingsTab):
|
||||
Called from ThemeManager when the Themes have changed
|
||||
"""
|
||||
#reload as may have been triggered by the ThemeManager
|
||||
self.global_theme = self.config.get_config(u'global theme', u'')
|
||||
self.global_theme = unicode(QtCore.QSettings().value(
|
||||
self.settingsSection + u'/global theme',
|
||||
QtCore.QVariant(u'')).toString())
|
||||
self.DefaultComboBox.clear()
|
||||
for theme in theme_list:
|
||||
self.DefaultComboBox.addItem(theme)
|
||||
|
@ -43,9 +43,10 @@ class AppLocation(object):
|
||||
ConfigDir = 2
|
||||
DataDir = 3
|
||||
PluginsDir = 4
|
||||
VersionDir = 5
|
||||
|
||||
@staticmethod
|
||||
def get_directory(dir_type):
|
||||
def get_directory(dir_type=1):
|
||||
"""
|
||||
Return the appropriate directory according to the directory type.
|
||||
|
||||
@ -63,7 +64,8 @@ class AppLocation(object):
|
||||
else:
|
||||
try:
|
||||
from xdg import BaseDirectory
|
||||
path = os.path.join(BaseDirectory.xdg_config_home, u'openlp')
|
||||
path = os.path.join(
|
||||
BaseDirectory.xdg_config_home, u'openlp')
|
||||
except ImportError:
|
||||
path = os.path.join(os.getenv(u'HOME'), u'.openlp')
|
||||
return path
|
||||
@ -83,39 +85,57 @@ class AppLocation(object):
|
||||
elif dir_type == AppLocation.PluginsDir:
|
||||
plugin_path = None
|
||||
app_path = os.path.abspath(os.path.split(sys.argv[0])[0])
|
||||
if sys.platform == u'win32':
|
||||
if hasattr(sys, u'frozen') and sys.frozen == 1:
|
||||
plugin_path = os.path.join(app_path, u'plugins')
|
||||
else:
|
||||
plugin_path = os.path.join(app_path, u'openlp', u'plugins')
|
||||
elif sys.platform == u'darwin':
|
||||
if hasattr(sys, u'frozen') and sys.frozen == 1:
|
||||
plugin_path = os.path.join(app_path, u'plugins')
|
||||
else:
|
||||
plugin_path = os.path.join(
|
||||
os.path.split(openlp.__file__)[0], u'plugins')
|
||||
return plugin_path
|
||||
elif dir_type == AppLocation.VersionDir:
|
||||
if hasattr(sys, u'frozen') and sys.frozen == 1:
|
||||
plugin_path = os.path.abspath(os.path.split(sys.argv[0])[0])
|
||||
else:
|
||||
plugin_path = os.path.split(openlp.__file__)[0]
|
||||
return plugin_path
|
||||
|
||||
@staticmethod
|
||||
def get_data_path():
|
||||
path = AppLocation.get_directory(AppLocation.DataDir)
|
||||
if not os.path.exists(path):
|
||||
os.makedirs(path)
|
||||
return path
|
||||
|
||||
@staticmethod
|
||||
def get_section_data_path(section):
|
||||
data_path = AppLocation.get_data_path()
|
||||
path = os.path.join(data_path, section)
|
||||
if not os.path.exists(path):
|
||||
os.makedirs(path)
|
||||
return path
|
||||
|
||||
|
||||
def check_latest_version(config, current_version):
|
||||
def check_latest_version(current_version):
|
||||
"""
|
||||
Check the latest version of OpenLP against the version file on the OpenLP
|
||||
site.
|
||||
|
||||
``config``
|
||||
The OpenLP config object.
|
||||
|
||||
``current_version``
|
||||
The current version of OpenLP.
|
||||
"""
|
||||
version_string = current_version[u'full']
|
||||
#set to prod in the distribution confif file.
|
||||
last_test = config.get_config(u'last version test', datetime.now().date())
|
||||
#set to prod in the distribution config file.
|
||||
settings = QtCore.QSettings()
|
||||
settings.beginGroup(u'general')
|
||||
last_test = unicode(settings.value(u'last version test',
|
||||
QtCore.QVariant(datetime.now().date())).toString())
|
||||
this_test = unicode(datetime.now().date())
|
||||
config.set_config(u'last version test', this_test)
|
||||
settings.setValue(u'last version test', QtCore.QVariant(this_test))
|
||||
settings.endGroup()
|
||||
if last_test != this_test:
|
||||
version_string = u''
|
||||
if current_version[u'build']:
|
||||
req = urllib2.Request(u'http://www.openlp.org/files/dev_version.txt')
|
||||
req = urllib2.Request(
|
||||
u'http://www.openlp.org/files/dev_version.txt')
|
||||
else:
|
||||
req = urllib2.Request(u'http://www.openlp.org/files/version.txt')
|
||||
req.add_header(u'User-Agent', u'OpenLP/%s' % current_version[u'full'])
|
||||
@ -147,7 +167,23 @@ def variant_to_unicode(variant):
|
||||
string = string_to_unicode(string)
|
||||
return string
|
||||
|
||||
from registry import Registry
|
||||
from confighelper import ConfigHelper
|
||||
def add_actions(target, actions):
|
||||
"""
|
||||
Adds multiple actions to a menu or toolbar in one command.
|
||||
|
||||
__all__ = [u'Registry', u'ConfigHelper', u'AppLocation', u'check_latest_version']
|
||||
``target``
|
||||
The menu or toolbar to add actions to.
|
||||
|
||||
``actions``
|
||||
The actions to be added. An action consisting of the keyword 'None'
|
||||
will result in a separator being inserted into the target.
|
||||
"""
|
||||
for action in actions:
|
||||
if action is None:
|
||||
target.addSeparator()
|
||||
else:
|
||||
target.addAction(action)
|
||||
|
||||
from languagemanager import LanguageManager
|
||||
|
||||
__all__ = [u'AppLocation', u'check_latest_version', u'add_actions', u'LanguageManager']
|
||||
|
@ -1,76 +0,0 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
# vim: autoindent shiftwidth=4 expandtab textwidth=80 tabstop=4 softtabstop=4
|
||||
|
||||
###############################################################################
|
||||
# OpenLP - Open Source Lyrics Projection #
|
||||
# --------------------------------------------------------------------------- #
|
||||
# Copyright (c) 2008-2010 Raoul Snyman #
|
||||
# Portions copyright (c) 2008-2010 Tim Bentley, Jonathan Corwin, Michael #
|
||||
# Gorven, Scott Guerrieri, Christian Richter, Maikel Stuivenberg, Martin #
|
||||
# Thompson, Jon Tibble, Carsten Tinggaard #
|
||||
# --------------------------------------------------------------------------- #
|
||||
# This program is free software; you can redistribute it and/or modify it #
|
||||
# under the terms of the GNU General Public License as published by the Free #
|
||||
# Software Foundation; version 2 of the License. #
|
||||
# #
|
||||
# This program is distributed in the hope that it will be useful, but WITHOUT #
|
||||
# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or #
|
||||
# FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for #
|
||||
# more details. #
|
||||
# #
|
||||
# You should have received a copy of the GNU General Public License along #
|
||||
# with this program; if not, write to the Free Software Foundation, Inc., 59 #
|
||||
# Temple Place, Suite 330, Boston, MA 02111-1307 USA #
|
||||
###############################################################################
|
||||
|
||||
import os
|
||||
|
||||
from openlp.core.utils import AppLocation
|
||||
from openlp.core.utils.registry import Registry
|
||||
|
||||
class ConfigHelper(object):
|
||||
"""
|
||||
Utility Helper to allow classes to find directories in a standard manner.
|
||||
"""
|
||||
__registry__ = None
|
||||
|
||||
@staticmethod
|
||||
def get_data_path():
|
||||
path = AppLocation.get_directory(AppLocation.DataDir)
|
||||
if not os.path.exists(path):
|
||||
os.makedirs(path)
|
||||
return path
|
||||
|
||||
@staticmethod
|
||||
def get_config(section, key, default=None):
|
||||
reg = ConfigHelper.get_registry()
|
||||
if reg.has_value(section, key):
|
||||
return reg.get_value(section, key, default)
|
||||
else:
|
||||
if default:
|
||||
ConfigHelper.set_config(section, key, default)
|
||||
return default
|
||||
|
||||
@staticmethod
|
||||
def set_config(section, key, value):
|
||||
reg = ConfigHelper.get_registry()
|
||||
if not reg.has_section(section):
|
||||
reg.create_section(section)
|
||||
return reg.set_value(section, key, value)
|
||||
|
||||
@staticmethod
|
||||
def delete_config(section, key):
|
||||
reg = ConfigHelper.get_registry()
|
||||
reg.delete_value(section, key)
|
||||
|
||||
@staticmethod
|
||||
def get_registry():
|
||||
"""
|
||||
This static method loads the appropriate registry class based on the
|
||||
current operating system, and returns an instantiation of that class.
|
||||
"""
|
||||
if ConfigHelper.__registry__ is None:
|
||||
config_path = AppLocation.get_directory(AppLocation.ConfigDir)
|
||||
ConfigHelper.__registry__ = Registry(config_path)
|
||||
return ConfigHelper.__registry__
|
||||
|
111
openlp/core/utils/languagemanager.py
Normal file
@ -0,0 +1,111 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
# vim: autoindent shiftwidth=4 expandtab textwidth=80 tabstop=4 softtabstop=4
|
||||
|
||||
###############################################################################
|
||||
# OpenLP - Open Source Lyrics Projection #
|
||||
# --------------------------------------------------------------------------- #
|
||||
# Copyright (c) 2008-2010 Raoul Snyman #
|
||||
# Portions copyright (c) 2008-2010 Tim Bentley, Jonathan Corwin, Michael #
|
||||
# Gorven, Scott Guerrieri, Christian Richter, Maikel Stuivenberg, Martin #
|
||||
# Thompson, Jon Tibble, Carsten Tinggaard #
|
||||
# --------------------------------------------------------------------------- #
|
||||
# This program is free software; you can redistribute it and/or modify it #
|
||||
# under the terms of the GNU General Public License as published by the Free #
|
||||
# Software Foundation; version 2 of the License. #
|
||||
# #
|
||||
# This program is distributed in the hope that it will be useful, but WITHOUT #
|
||||
# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or #
|
||||
# FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for #
|
||||
# more details. #
|
||||
# #
|
||||
# You should have received a copy of the GNU General Public License along #
|
||||
# with this program; if not, write to the Free Software Foundation, Inc., 59 #
|
||||
# Temple Place, Suite 330, Boston, MA 02111-1307 USA #
|
||||
###############################################################################
|
||||
|
||||
import logging
|
||||
import os
|
||||
|
||||
from PyQt4 import QtCore, QtGui
|
||||
from openlp.core.utils import AppLocation
|
||||
from openlp.core.lib import translate
|
||||
|
||||
log = logging.getLogger()
|
||||
|
||||
class LanguageManager(object):
|
||||
"""
|
||||
Helper for Language selection
|
||||
"""
|
||||
__qmList__ = None
|
||||
AutoLanguage = False
|
||||
|
||||
@staticmethod
|
||||
def get_translator(language):
|
||||
if LanguageManager.AutoLanguage :
|
||||
language = QtCore.QLocale.system().name()
|
||||
lang_Path = AppLocation.get_directory(AppLocation.AppDir)
|
||||
lang_Path = os.path.join(lang_Path, u'resources', u'i18n')
|
||||
appTranslator = QtCore.QTranslator()
|
||||
if appTranslator.load("openlp_" + language, lang_Path):
|
||||
return appTranslator
|
||||
|
||||
@staticmethod
|
||||
def find_qm_files():
|
||||
trans_dir = AppLocation.get_directory(AppLocation.AppDir)
|
||||
trans_dir = QtCore.QDir(os.path.join(trans_dir, u'resources', u'i18n'))
|
||||
fileNames = trans_dir.entryList(QtCore.QStringList("*.qm"),
|
||||
QtCore.QDir.Files, QtCore.QDir.Name)
|
||||
for i in fileNames:
|
||||
fileNames.replaceInStrings(i, trans_dir.filePath(i))
|
||||
return fileNames
|
||||
|
||||
@staticmethod
|
||||
def language_name(qmFile):
|
||||
translator = QtCore.QTranslator()
|
||||
translator.load(qmFile)
|
||||
return translator.translate(u'MainWindow', u'English')
|
||||
|
||||
@staticmethod
|
||||
def get_language():
|
||||
settings = QtCore.QSettings(u'OpenLP', u'OpenLP')
|
||||
language = unicode(settings.value(
|
||||
u'general/language', QtCore.QVariant(u'[en]')).toString())
|
||||
log.info(u'Language file: \'%s\' Loaded from conf file' % language)
|
||||
regEx = QtCore.QRegExp("^\[(.*)\]")
|
||||
if regEx.exactMatch(language):
|
||||
LanguageManager.AutoLanguage = True
|
||||
language = regEx.cap(1)
|
||||
return language
|
||||
|
||||
@staticmethod
|
||||
def set_language(action):
|
||||
actionName = u'%s' % action.objectName()
|
||||
qmList = LanguageManager.get_qm_list()
|
||||
if LanguageManager.AutoLanguage :
|
||||
language = u'[%s]' % qmList[actionName]
|
||||
else:
|
||||
language = u'%s' % qmList[actionName]
|
||||
QtCore.QSettings().setValue(
|
||||
u'general/language', QtCore.QVariant(language))
|
||||
log.info(u'Language file: \'%s\' written to conf file' % language)
|
||||
QtGui.QMessageBox.information(None,
|
||||
translate('LanguageManager', 'Language'),
|
||||
translate('LanguageManager',
|
||||
'After restart new Language settings will be used.'))
|
||||
|
||||
@staticmethod
|
||||
def init_qm_list():
|
||||
LanguageManager.__qmList__ = {}
|
||||
qmFiles = LanguageManager.find_qm_files()
|
||||
for i, qmf in enumerate(qmFiles):
|
||||
regEx = QtCore.QRegExp("^.*openlp_(.*).qm")
|
||||
if regEx.exactMatch(qmf):
|
||||
langName = regEx.cap(1)
|
||||
LanguageManager.__qmList__[u'%#2i %s' % (i+1,
|
||||
LanguageManager.language_name(qmf))] = langName
|
||||
|
||||
@staticmethod
|
||||
def get_qm_list():
|
||||
if LanguageManager.__qmList__ == None:
|
||||
LanguageManager.init_qm_list()
|
||||
return LanguageManager.__qmList__
|
@ -1,130 +0,0 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
# vim: autoindent shiftwidth=4 expandtab textwidth=80 tabstop=4 softtabstop=4
|
||||
|
||||
###############################################################################
|
||||
# OpenLP - Open Source Lyrics Projection #
|
||||
# --------------------------------------------------------------------------- #
|
||||
# Copyright (c) 2008-2010 Raoul Snyman #
|
||||
# Portions copyright (c) 2008-2010 Tim Bentley, Jonathan Corwin, Michael #
|
||||
# Gorven, Scott Guerrieri, Christian Richter, Maikel Stuivenberg, Martin #
|
||||
# Thompson, Jon Tibble, Carsten Tinggaard #
|
||||
# --------------------------------------------------------------------------- #
|
||||
# This program is free software; you can redistribute it and/or modify it #
|
||||
# under the terms of the GNU General Public License as published by the Free #
|
||||
# Software Foundation; version 2 of the License. #
|
||||
# #
|
||||
# This program is distributed in the hope that it will be useful, but WITHOUT #
|
||||
# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or #
|
||||
# FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for #
|
||||
# more details. #
|
||||
# #
|
||||
# You should have received a copy of the GNU General Public License along #
|
||||
# with this program; if not, write to the Free Software Foundation, Inc., 59 #
|
||||
# Temple Place, Suite 330, Boston, MA 02111-1307 USA #
|
||||
###############################################################################
|
||||
|
||||
import os
|
||||
|
||||
from ConfigParser import SafeConfigParser
|
||||
|
||||
class Registry(object):
|
||||
"""
|
||||
The Registry class is a high-level class for working with a configuration
|
||||
file.
|
||||
"""
|
||||
def __init__(self, dir):
|
||||
self.config = SafeConfigParser()
|
||||
self.file_name = os.path.join(dir, u'openlp.conf')
|
||||
self._load()
|
||||
|
||||
def has_value(self, section, key):
|
||||
"""
|
||||
Check if a value exists.
|
||||
"""
|
||||
return self.config.has_option(section, key)
|
||||
|
||||
def get_value(self, section, key, default=None):
|
||||
"""
|
||||
Get a single value from the registry.
|
||||
"""
|
||||
try:
|
||||
if self.config.get(section, key):
|
||||
return self.config.get(section, key)
|
||||
else:
|
||||
return default
|
||||
except:
|
||||
return default
|
||||
|
||||
def set_value(self, section, key, value):
|
||||
"""
|
||||
Set a single value in the registry.
|
||||
"""
|
||||
try :
|
||||
self.config.set(section, key, unicode(value))
|
||||
return self._save()
|
||||
except:
|
||||
return False
|
||||
|
||||
def delete_value(self, section, key):
|
||||
"""
|
||||
Delete a single value from the registry.
|
||||
"""
|
||||
try:
|
||||
self.config.remove_option(section, key)
|
||||
return self._save()
|
||||
except:
|
||||
return False
|
||||
|
||||
def has_section(self, section):
|
||||
"""
|
||||
Check if a section exists.
|
||||
"""
|
||||
return self.config.has_section(section)
|
||||
|
||||
def create_section(self, section):
|
||||
"""
|
||||
Create a new section in the registry.
|
||||
"""
|
||||
try:
|
||||
self.config.add_section(section)
|
||||
return self._save()
|
||||
except:
|
||||
return False
|
||||
|
||||
def delete_section(self, section):
|
||||
"""
|
||||
Delete a section (including all values).
|
||||
"""
|
||||
try:
|
||||
self.config.remove_section(section)
|
||||
return self._save()
|
||||
except:
|
||||
return False
|
||||
|
||||
def _load(self):
|
||||
if not os.path.isfile(self.file_name):
|
||||
return False
|
||||
file_handle = None
|
||||
try:
|
||||
file_handle = open(self.file_name, u'r')
|
||||
self.config.readfp(file_handle)
|
||||
return True
|
||||
except:
|
||||
return False
|
||||
finally:
|
||||
if file_handle:
|
||||
file_handle.close()
|
||||
|
||||
def _save(self):
|
||||
file_handle = None
|
||||
try:
|
||||
if not os.path.exists(os.path.dirname(self.file_name)):
|
||||
os.makedirs(os.path.dirname(self.file_name))
|
||||
file_handle = open(self.file_name, u'w')
|
||||
self.config.write(file_handle)
|
||||
return self._load()
|
||||
except:
|
||||
return False
|
||||
finally:
|
||||
if file_handle:
|
||||
file_handle.close()
|
@ -31,7 +31,8 @@ from sqlalchemy import *
|
||||
from sqlalchemy import create_engine
|
||||
from sqlalchemy.orm import scoped_session, sessionmaker, mapper
|
||||
|
||||
from openlp.core.lib import PluginConfig
|
||||
from openlp.core.lib import SettingsManager
|
||||
from openlp.core.utils import AppLocation
|
||||
from openlp.plugins.bibles.lib.models import *
|
||||
|
||||
class BaseModel(object):
|
||||
@ -111,9 +112,8 @@ def init_models(url):
|
||||
class MigrateBibles():
|
||||
def __init__(self, display):
|
||||
self.display = display
|
||||
self.config = PluginConfig(u'Bibles')
|
||||
self.data_path = self.config.get_data_path()
|
||||
self.database_files = self.config.get_files(u'sqlite')
|
||||
self.data_path = AppLocation.get_section_data_path(u'bibles')
|
||||
self.database_files = SettingsManager.get_files(u'bibles', u'.sqlite')
|
||||
print self.database_files
|
||||
|
||||
def progress(self, text):
|
||||
|
@ -23,7 +23,7 @@
|
||||
# Temple Place, Suite 330, Boston, MA 02111-1307 USA #
|
||||
###############################################################################
|
||||
|
||||
from openlp.core.utils import ConfigHelper
|
||||
from openlp.core.utils import AppLocation
|
||||
|
||||
class MigrateFiles():
|
||||
def __init__(self, display):
|
||||
@ -36,14 +36,19 @@ class MigrateFiles():
|
||||
|
||||
def _initial_setup(self):
|
||||
self.display.output(u'Initial Setup started')
|
||||
ConfigHelper.get_data_path()
|
||||
data_path = AppLocation.get_data_path()
|
||||
print data_path
|
||||
self.display.sub_output(u'Config created')
|
||||
ConfigHelper.get_config(u'bible', u'data path')
|
||||
bibles_path = AppLocation.get_section_data_path(u'bibles')
|
||||
print bibles_path
|
||||
self.display.sub_output(u'Config created')
|
||||
ConfigHelper.get_config(u'videos', u'data path')
|
||||
self.display.sub_output(u'videos created')
|
||||
ConfigHelper.get_config(u'images', u'data path')
|
||||
# Media doesn't use a directory like the other plugins.
|
||||
#media_path = AppLocation.get_section_data_path(u'media')
|
||||
#self.display.sub_output(u'videos created')
|
||||
images_path = AppLocation.get_section_data_path(u'images')
|
||||
print images_path
|
||||
self.display.sub_output(u'images created')
|
||||
ConfigHelper.get_config(u'presentations', u'data path')
|
||||
presentations_path = AppLocation.get_section_data_path(u'presentations')
|
||||
print presentations_path
|
||||
self.display.sub_output(u'presentations created')
|
||||
self.display.output(u'Initial Setup finished')
|
||||
|
@ -31,7 +31,8 @@ from sqlalchemy import *
|
||||
from sqlalchemy import create_engine
|
||||
from sqlalchemy.orm import scoped_session, sessionmaker, mapper, relation
|
||||
|
||||
from openlp.core.lib import PluginConfig
|
||||
from openlp.core.lib import SettingsManager
|
||||
from openlp.core.utils import AppLocation
|
||||
from openlp.plugins.songs.lib.models import metadata, songs_table, Song, \
|
||||
Author, Topic, Book
|
||||
from openlp.plugins.songs.lib.tables import *
|
||||
@ -46,7 +47,7 @@ def init_models(url):
|
||||
mapper(TAuthor, temp_authors_table)
|
||||
mapper(Book, song_books_table)
|
||||
mapper(Song, songs_table,
|
||||
properties={'authors': relation(Author, backref='songs',
|
||||
properties={'authors': relation(Author, backref='songs',
|
||||
secondary=authors_songs_table),
|
||||
'book': relation(Book, backref='songs'),
|
||||
'topics': relation(Topic, backref='songs',
|
||||
@ -111,9 +112,8 @@ class TSongAuthor(BaseModel):
|
||||
class MigrateSongs():
|
||||
def __init__(self, display):
|
||||
self.display = display
|
||||
self.config = PluginConfig(u'Songs')
|
||||
self.data_path = self.config.get_data_path()
|
||||
self.database_files = self.config.get_files(u'sqlite')
|
||||
self.data_path = AppLocation.get_section_data_path(u'songs')
|
||||
self.database_files = SettingsManager.get_files(u'songs', u'.sqlite')
|
||||
print self.database_files
|
||||
|
||||
def process(self):
|
||||
@ -156,13 +156,13 @@ class MigrateSongs():
|
||||
print songs_temp.songtitle
|
||||
aa = self.session.execute(
|
||||
u'select * from songauthors_temp where songid =' + \
|
||||
unicode(songs_temp.songid) )
|
||||
unicode(songs_temp.songid))
|
||||
for row in aa:
|
||||
a = row['authorid']
|
||||
authors_temp = self.session.query(TAuthor).get(a)
|
||||
bb = self.session.execute(
|
||||
u'select * from authors where display_name = \"%s\"' % \
|
||||
unicode(authors_temp.authorname) ).fetchone()
|
||||
unicode(authors_temp.authorname)).fetchone()
|
||||
if bb is None:
|
||||
author = Author()
|
||||
author.display_name = authors_temp.authorname
|
||||
|
@ -28,8 +28,8 @@ import logging
|
||||
from PyQt4 import QtCore, QtGui
|
||||
|
||||
from openlp.core.lib import Plugin, build_icon, PluginStatus
|
||||
from openlp.plugins.alerts.lib import AlertsManager, DBManager
|
||||
from openlp.plugins.alerts.forms import AlertsTab, AlertForm
|
||||
from openlp.plugins.alerts.lib import AlertsManager, AlertsTab, DBManager
|
||||
from openlp.plugins.alerts.forms import AlertForm
|
||||
|
||||
log = logging.getLogger(__name__)
|
||||
|
||||
@ -41,7 +41,7 @@ class alertsPlugin(Plugin):
|
||||
self.weight = -3
|
||||
self.icon = build_icon(u':/media/media_image.png')
|
||||
self.alertsmanager = AlertsManager(self)
|
||||
self.manager = DBManager(self.config)
|
||||
self.manager = DBManager()
|
||||
self.alertForm = AlertForm(self.manager, self)
|
||||
self.status = PluginStatus.Active
|
||||
|
||||
@ -83,7 +83,9 @@ class alertsPlugin(Plugin):
|
||||
|
||||
def togglealertsState(self):
|
||||
self.alertsActive = not self.alertsActive
|
||||
self.config.set_config(u'active', self.alertsActive)
|
||||
QtCore.QSettings().setValue(
|
||||
self.settingsSection + u'/active',
|
||||
QtCore.QVariant(self.alertsActive))
|
||||
|
||||
def onAlertsTrigger(self):
|
||||
self.alertForm.loadList()
|
||||
|
@ -23,5 +23,4 @@
|
||||
# Temple Place, Suite 330, Boston, MA 02111-1307 USA #
|
||||
###############################################################################
|
||||
|
||||
from alertstab import AlertsTab
|
||||
from alertform import AlertForm
|
||||
|
@ -24,64 +24,123 @@
|
||||
###############################################################################
|
||||
|
||||
from PyQt4 import QtCore, QtGui
|
||||
from openlp.core.lib import translate
|
||||
|
||||
class Ui_AlertDialog(object):
|
||||
def setupUi(self, AlertForm):
|
||||
AlertForm.setObjectName(u'AlertDialog')
|
||||
AlertForm.resize(430, 320)
|
||||
def setupUi(self, AlertDialog):
|
||||
AlertDialog.setObjectName(u'AlertDialog')
|
||||
AlertDialog.resize(567, 440)
|
||||
icon = QtGui.QIcon()
|
||||
icon.addPixmap(QtGui.QPixmap(u':/icon/openlp.org-icon-32.bmp'), QtGui.QIcon.Normal, QtGui.QIcon.Off)
|
||||
AlertForm.setWindowIcon(icon)
|
||||
self.AlertFormLayout = QtGui.QVBoxLayout(AlertForm)
|
||||
self.AlertFormLayout.setSpacing(8)
|
||||
self.AlertFormLayout.setMargin(8)
|
||||
self.AlertFormLayout.setObjectName(u'AlertFormLayout')
|
||||
self.AlertEntryWidget = QtGui.QWidget(AlertForm)
|
||||
sizePolicy = QtGui.QSizePolicy(QtGui.QSizePolicy.Preferred, QtGui.QSizePolicy.Preferred)
|
||||
sizePolicy.setHorizontalStretch(0)
|
||||
sizePolicy.setVerticalStretch(0)
|
||||
sizePolicy.setHeightForWidth(self.AlertEntryWidget.sizePolicy().hasHeightForWidth())
|
||||
self.AlertEntryWidget.setSizePolicy(sizePolicy)
|
||||
self.AlertEntryWidget.setObjectName(u'AlertEntryWidget')
|
||||
self.verticalLayout_2 = QtGui.QVBoxLayout(self.AlertEntryWidget)
|
||||
self.verticalLayout_2.setObjectName(u'verticalLayout_2')
|
||||
self.verticalLayout = QtGui.QVBoxLayout()
|
||||
self.verticalLayout.setObjectName(u'verticalLayout')
|
||||
self.AlertEntryLabel = QtGui.QLabel(self.AlertEntryWidget)
|
||||
AlertDialog.setWindowIcon(icon)
|
||||
self.AlertDialogLayout = QtGui.QVBoxLayout(AlertDialog)
|
||||
self.AlertDialogLayout.setSpacing(8)
|
||||
self.AlertDialogLayout.setMargin(8)
|
||||
self.AlertDialogLayout.setObjectName(u'AlertDialogLayout')
|
||||
self.AlertTextLayout = QtGui.QFormLayout()
|
||||
self.AlertTextLayout.setContentsMargins(0, 0, -1, -1)
|
||||
self.AlertTextLayout.setSpacing(8)
|
||||
self.AlertTextLayout.setObjectName(u'AlertTextLayout')
|
||||
self.AlertEntryLabel = QtGui.QLabel(AlertDialog)
|
||||
sizePolicy = QtGui.QSizePolicy(QtGui.QSizePolicy.Preferred, QtGui.QSizePolicy.Fixed)
|
||||
sizePolicy.setHorizontalStretch(0)
|
||||
sizePolicy.setVerticalStretch(0)
|
||||
sizePolicy.setHeightForWidth(self.AlertEntryLabel.sizePolicy().hasHeightForWidth())
|
||||
self.AlertEntryLabel.setSizePolicy(sizePolicy)
|
||||
self.AlertEntryLabel.setObjectName(u'AlertEntryLabel')
|
||||
self.verticalLayout.addWidget(self.AlertEntryLabel)
|
||||
self.AlertEntryEditItem = QtGui.QLineEdit(self.AlertEntryWidget)
|
||||
self.AlertEntryEditItem.setObjectName(u'AlertEntryEditItem')
|
||||
self.verticalLayout.addWidget(self.AlertEntryEditItem)
|
||||
self.AlertListWidget = QtGui.QListWidget(self.AlertEntryWidget)
|
||||
self.AlertTextLayout.setWidget(0, QtGui.QFormLayout.LabelRole, self.AlertEntryLabel)
|
||||
self.AlertParameter = QtGui.QLabel(AlertDialog)
|
||||
self.AlertParameter.setObjectName(u'AlertParameter')
|
||||
self.AlertTextLayout.setWidget(1, QtGui.QFormLayout.LabelRole, self.AlertParameter)
|
||||
self.ParameterEdit = QtGui.QLineEdit(AlertDialog)
|
||||
self.ParameterEdit.setObjectName(u'ParameterEdit')
|
||||
self.AlertTextLayout.setWidget(1, QtGui.QFormLayout.FieldRole, self.ParameterEdit)
|
||||
self.AlertTextEdit = QtGui.QLineEdit(AlertDialog)
|
||||
self.AlertTextEdit.setObjectName(u'AlertTextEdit')
|
||||
self.AlertTextLayout.setWidget(0, QtGui.QFormLayout.FieldRole, self.AlertTextEdit)
|
||||
self.AlertDialogLayout.addLayout(self.AlertTextLayout)
|
||||
self.ManagementLayout = QtGui.QHBoxLayout()
|
||||
self.ManagementLayout.setSpacing(8)
|
||||
self.ManagementLayout.setContentsMargins(-1, -1, -1, 0)
|
||||
self.ManagementLayout.setObjectName(u'ManagementLayout')
|
||||
self.AlertListWidget = QtGui.QListWidget(AlertDialog)
|
||||
self.AlertListWidget.setAlternatingRowColors(True)
|
||||
self.AlertListWidget.setObjectName(u'AlertListWidget')
|
||||
self.verticalLayout.addWidget(self.AlertListWidget)
|
||||
self.verticalLayout_2.addLayout(self.verticalLayout)
|
||||
self.horizontalLayout = QtGui.QHBoxLayout()
|
||||
self.horizontalLayout.setObjectName(u'horizontalLayout')
|
||||
spacerItem = QtGui.QSpacerItem(181, 38, QtGui.QSizePolicy.Expanding, QtGui.QSizePolicy.Minimum)
|
||||
self.horizontalLayout.addItem(spacerItem)
|
||||
self.DisplayButton = QtGui.QPushButton(self.AlertEntryWidget)
|
||||
self.ManagementLayout.addWidget(self.AlertListWidget)
|
||||
self.ManageButtonLayout = QtGui.QVBoxLayout()
|
||||
self.ManageButtonLayout.setSpacing(8)
|
||||
self.ManageButtonLayout.setObjectName(u'ManageButtonLayout')
|
||||
self.NewButton = QtGui.QPushButton(AlertDialog)
|
||||
icon1 = QtGui.QIcon()
|
||||
icon1.addPixmap(QtGui.QPixmap(u':/general/general_new.png'), QtGui.QIcon.Normal, QtGui.QIcon.Off)
|
||||
self.NewButton.setIcon(icon1)
|
||||
self.NewButton.setObjectName(u'NewButton')
|
||||
self.ManageButtonLayout.addWidget(self.NewButton)
|
||||
self.SaveButton = QtGui.QPushButton(AlertDialog)
|
||||
self.SaveButton.setEnabled(False)
|
||||
icon2 = QtGui.QIcon()
|
||||
icon2.addPixmap(QtGui.QPixmap(u':/general/general_save.png'), QtGui.QIcon.Normal, QtGui.QIcon.Off)
|
||||
self.SaveButton.setIcon(icon2)
|
||||
self.SaveButton.setObjectName(u'SaveButton')
|
||||
self.ManageButtonLayout.addWidget(self.SaveButton)
|
||||
self.DeleteButton = QtGui.QPushButton(AlertDialog)
|
||||
icon3 = QtGui.QIcon()
|
||||
icon3.addPixmap(QtGui.QPixmap(u':/general/general_delete.png'), QtGui.QIcon.Normal, QtGui.QIcon.Off)
|
||||
self.DeleteButton.setIcon(icon3)
|
||||
self.DeleteButton.setObjectName(u'DeleteButton')
|
||||
self.ManageButtonLayout.addWidget(self.DeleteButton)
|
||||
spacerItem = QtGui.QSpacerItem(20, 40, QtGui.QSizePolicy.Minimum, QtGui.QSizePolicy.Expanding)
|
||||
self.ManageButtonLayout.addItem(spacerItem)
|
||||
self.ManagementLayout.addLayout(self.ManageButtonLayout)
|
||||
self.AlertDialogLayout.addLayout(self.ManagementLayout)
|
||||
self.AlertButtonLayout = QtGui.QHBoxLayout()
|
||||
self.AlertButtonLayout.setSpacing(8)
|
||||
self.AlertButtonLayout.setObjectName(u'AlertButtonLayout')
|
||||
spacerItem1 = QtGui.QSpacerItem(181, 0, QtGui.QSizePolicy.Expanding,
|
||||
QtGui.QSizePolicy.Minimum)
|
||||
self.AlertButtonLayout.addItem(spacerItem1)
|
||||
self.DisplayButton = QtGui.QPushButton(AlertDialog)
|
||||
icon4 = QtGui.QIcon()
|
||||
icon4.addPixmap(QtGui.QPixmap(u':/general/general_live.png'),
|
||||
QtGui.QIcon.Normal, QtGui.QIcon.Off)
|
||||
self.DisplayButton.setIcon(icon4)
|
||||
self.DisplayButton.setObjectName(u'DisplayButton')
|
||||
self.horizontalLayout.addWidget(self.DisplayButton)
|
||||
self.CancelButton = QtGui.QPushButton(self.AlertEntryWidget)
|
||||
self.CancelButton.setObjectName(u'CancelButton')
|
||||
self.horizontalLayout.addWidget(self.CancelButton)
|
||||
self.verticalLayout_2.addLayout(self.horizontalLayout)
|
||||
self.AlertFormLayout.addWidget(self.AlertEntryWidget)
|
||||
self.AlertButtonLayout.addWidget(self.DisplayButton)
|
||||
self.DisplayCloseButton = QtGui.QPushButton(AlertDialog)
|
||||
self.DisplayCloseButton.setIcon(icon4)
|
||||
self.DisplayCloseButton.setObjectName(u'DisplayCloseButton')
|
||||
self.AlertButtonLayout.addWidget(self.DisplayCloseButton)
|
||||
self.CloseButton = QtGui.QPushButton(AlertDialog)
|
||||
icon5 = QtGui.QIcon()
|
||||
icon5.addPixmap(QtGui.QPixmap(u':/system/system_close.png'),
|
||||
QtGui.QIcon.Normal, QtGui.QIcon.Off)
|
||||
self.CloseButton.setIcon(icon5)
|
||||
self.CloseButton.setObjectName(u'CloseButton')
|
||||
self.AlertButtonLayout.addWidget(self.CloseButton)
|
||||
self.AlertDialogLayout.addLayout(self.AlertButtonLayout)
|
||||
self.AlertEntryLabel.setBuddy(self.AlertTextEdit)
|
||||
self.AlertParameter.setBuddy(self.ParameterEdit)
|
||||
|
||||
self.retranslateUi(AlertForm)
|
||||
QtCore.QObject.connect(self.CancelButton, QtCore.SIGNAL(u'clicked()'), self.close)
|
||||
QtCore.QMetaObject.connectSlotsByName(AlertForm)
|
||||
self.retranslateUi(AlertDialog)
|
||||
QtCore.QObject.connect(self.CloseButton, QtCore.SIGNAL(u'clicked()'), AlertDialog.close)
|
||||
QtCore.QMetaObject.connectSlotsByName(AlertDialog)
|
||||
AlertDialog.setTabOrder(self.AlertTextEdit, self.ParameterEdit)
|
||||
AlertDialog.setTabOrder(self.ParameterEdit, self.AlertListWidget)
|
||||
AlertDialog.setTabOrder(self.AlertListWidget, self.NewButton)
|
||||
AlertDialog.setTabOrder(self.NewButton, self.SaveButton)
|
||||
AlertDialog.setTabOrder(self.SaveButton, self.DeleteButton)
|
||||
AlertDialog.setTabOrder(self.DeleteButton, self.DisplayButton)
|
||||
AlertDialog.setTabOrder(self.DisplayButton, self.DisplayCloseButton)
|
||||
AlertDialog.setTabOrder(self.DisplayCloseButton, self.CloseButton)
|
||||
|
||||
def retranslateUi(self, AlertDialog):
|
||||
AlertDialog.setWindowTitle(translate('AlertForm', 'Alert Message'))
|
||||
self.AlertEntryLabel.setText(translate('AlertForm', 'Alert &text:'))
|
||||
self.AlertParameter.setText(translate('AlertForm', '&Parameter(s):'))
|
||||
self.NewButton.setText(translate('AlertForm', '&New'))
|
||||
self.SaveButton.setText(translate('AlertForm', '&Save'))
|
||||
self.DeleteButton.setText(translate('AlertForm', '&Delete'))
|
||||
self.DisplayButton.setText(translate('AlertForm', 'Displ&ay'))
|
||||
self.DisplayCloseButton.setText(translate('AlertForm', 'Display && Cl&ose'))
|
||||
self.CloseButton.setText(translate('AlertForm', '&Close'))
|
||||
|
||||
def retranslateUi(self, AlertForm):
|
||||
AlertForm.setWindowTitle(self.trUtf8('Alert Message'))
|
||||
self.AlertEntryLabel.setText(self.trUtf8('Alert Text:'))
|
||||
self.DisplayButton.setText(self.trUtf8('Display'))
|
||||
self.CancelButton.setText(self.trUtf8('Cancel'))
|
||||
|
@ -39,15 +39,27 @@ class AlertForm(QtGui.QDialog, Ui_AlertDialog):
|
||||
"""
|
||||
self.manager = manager
|
||||
self.parent = parent
|
||||
self.history_required = True
|
||||
self.item_id = None
|
||||
QtGui.QDialog.__init__(self, None)
|
||||
self.setupUi(self)
|
||||
QtCore.QObject.connect(self.DisplayButton,
|
||||
QtCore.SIGNAL(u'clicked()'),
|
||||
self.onDisplayClicked)
|
||||
QtCore.QObject.connect(self.AlertEntryEditItem,
|
||||
QtCore.QObject.connect(self.DisplayCloseButton,
|
||||
QtCore.SIGNAL(u'clicked()'),
|
||||
self.onDisplayCloseClicked)
|
||||
QtCore.QObject.connect(self.AlertTextEdit,
|
||||
QtCore.SIGNAL(u'textChanged(const QString&)'),
|
||||
self.onTextChanged)
|
||||
QtCore.QObject.connect(self.NewButton,
|
||||
QtCore.SIGNAL(u'clicked()'),
|
||||
self.onNewClick)
|
||||
QtCore.QObject.connect(self.DeleteButton,
|
||||
QtCore.SIGNAL(u'clicked()'),
|
||||
self.onDeleteClick)
|
||||
QtCore.QObject.connect(self.SaveButton,
|
||||
QtCore.SIGNAL(u'clicked()'),
|
||||
self.onSaveClick)
|
||||
QtCore.QObject.connect(self.AlertListWidget,
|
||||
QtCore.SIGNAL(u'doubleClicked(QModelIndex)'),
|
||||
self.onDoubleClick)
|
||||
@ -60,20 +72,57 @@ class AlertForm(QtGui.QDialog, Ui_AlertDialog):
|
||||
alerts = self.manager.get_all_alerts()
|
||||
for alert in alerts:
|
||||
item_name = QtGui.QListWidgetItem(alert.text)
|
||||
item_name.setData(
|
||||
QtCore.Qt.UserRole, QtCore.QVariant(alert.id))
|
||||
self.AlertListWidget.addItem(item_name)
|
||||
self.SaveButton.setEnabled(False)
|
||||
self.DeleteButton.setEnabled(False)
|
||||
|
||||
def onDisplayClicked(self):
|
||||
self.triggerAlert(unicode(self.AlertEntryEditItem.text()))
|
||||
if self.parent.alertsTab.save_history and self.history_required:
|
||||
if self.triggerAlert(unicode(self.AlertTextEdit.text())):
|
||||
self.loadList()
|
||||
|
||||
def onDisplayCloseClicked(self):
|
||||
if self.triggerAlert(unicode(self.AlertTextEdit.text())):
|
||||
self.close()
|
||||
|
||||
def onDeleteClick(self):
|
||||
item = self.AlertListWidget.currentItem()
|
||||
if item:
|
||||
item_id = (item.data(QtCore.Qt.UserRole)).toInt()[0]
|
||||
self.parent.manager.delete_alert(item_id)
|
||||
row = self.AlertListWidget.row(item)
|
||||
self.AlertListWidget.takeItem(row)
|
||||
self.AlertTextEdit.setText(u'')
|
||||
self.SaveButton.setEnabled(False)
|
||||
self.DeleteButton.setEnabled(False)
|
||||
self.EditButton.setEnabled(False)
|
||||
|
||||
def onNewClick(self):
|
||||
if len(self.AlertTextEdit.text()) == 0:
|
||||
QtGui.QMessageBox.information(self,
|
||||
self.trUtf8('Item selected to Add'),
|
||||
self.trUtf8('Missing data'))
|
||||
else:
|
||||
alert = AlertItem()
|
||||
alert.text = unicode(self.AlertEntryEditItem.text())
|
||||
alert.text = unicode(self.AlertTextEdit.text())
|
||||
self.manager.save_alert(alert)
|
||||
self.history_required = False
|
||||
self.AlertTextEdit.setText(u'')
|
||||
self.loadList()
|
||||
|
||||
def onSaveClick(self):
|
||||
if self.item_id:
|
||||
alert = self.manager.get_alert(self.item_id)
|
||||
alert.text = unicode(self.AlertTextEdit.text())
|
||||
self.manager.save_alert(alert)
|
||||
self.item_id = None
|
||||
self.loadList()
|
||||
else:
|
||||
self.onNewClick()
|
||||
|
||||
def onTextChanged(self):
|
||||
#Data has changed by editing it so potential storage
|
||||
self.history_required = True
|
||||
#Data has changed by editing it so potential storage required
|
||||
self.SaveButton.setEnabled(True)
|
||||
|
||||
def onDoubleClick(self):
|
||||
"""
|
||||
@ -83,7 +132,10 @@ class AlertForm(QtGui.QDialog, Ui_AlertDialog):
|
||||
for item in items:
|
||||
bitem = self.AlertListWidget.item(item.row())
|
||||
self.triggerAlert(bitem.text())
|
||||
self.history_required = False
|
||||
self.AlertTextEdit.setText(bitem.text())
|
||||
self.item_id = (bitem.data(QtCore.Qt.UserRole)).toInt()[0]
|
||||
self.SaveButton.setEnabled(False)
|
||||
self.DeleteButton.setEnabled(True)
|
||||
|
||||
def onSingleClick(self):
|
||||
"""
|
||||
@ -93,8 +145,14 @@ class AlertForm(QtGui.QDialog, Ui_AlertDialog):
|
||||
items = self.AlertListWidget.selectedIndexes()
|
||||
for item in items:
|
||||
bitem = self.AlertListWidget.item(item.row())
|
||||
self.AlertEntryEditItem.setText(bitem.text())
|
||||
self.history_required = False
|
||||
self.AlertTextEdit.setText(bitem.text())
|
||||
self.item_id = (bitem.data(QtCore.Qt.UserRole)).toInt()[0]
|
||||
self.SaveButton.setEnabled(False)
|
||||
self.DeleteButton.setEnabled(True)
|
||||
|
||||
def triggerAlert(self, text):
|
||||
self.parent.alertsmanager.displayAlert(text)
|
||||
if text:
|
||||
text = text.replace(u'<>', unicode(self.ParameterEdit.text()))
|
||||
self.parent.alertsmanager.displayAlert(text)
|
||||
return True
|
||||
return False
|
||||
|
@ -24,4 +24,5 @@
|
||||
###############################################################################
|
||||
|
||||
from alertsmanager import AlertsManager
|
||||
from alertstab import AlertsTab
|
||||
from manager import DBManager
|
||||
|
@ -40,21 +40,20 @@ class AlertsManager(QtCore.QObject):
|
||||
def __init__(self, parent):
|
||||
QtCore.QObject.__init__(self)
|
||||
self.parent = parent
|
||||
self.screen = None
|
||||
self.timer_id = 0
|
||||
self.alertList = []
|
||||
QtCore.QObject.connect(Receiver.get_receiver(),
|
||||
QtCore.SIGNAL(u'flush_alert'), self.generateAlert)
|
||||
QtCore.SIGNAL(u'maindisplay_active'), self.generateAlert)
|
||||
QtCore.QObject.connect(Receiver.get_receiver(),
|
||||
QtCore.SIGNAL(u'alert_text'), self.displayAlert)
|
||||
QtCore.SIGNAL(u'alerts_text'), self.onAlertText)
|
||||
QtCore.QObject.connect(Receiver.get_receiver(),
|
||||
QtCore.SIGNAL(u'screen_changed'), self.screenChanged)
|
||||
QtCore.QObject.connect(Receiver.get_receiver(),
|
||||
QtCore.SIGNAL(u'config_updated'), self.screenChanged)
|
||||
QtCore.SIGNAL(u'config_screen_changed'), self.screenChanged)
|
||||
|
||||
def screenChanged(self):
|
||||
log.debug(u'screen changed')
|
||||
self.screen = self.parent.maindisplay.screen
|
||||
self.alertTab = self.parent.alertsTab
|
||||
self.screen = self.parent.maindisplay.screens.current
|
||||
self.font = QtGui.QFont()
|
||||
self.font.setFamily(self.alertTab.font_face)
|
||||
self.font.setBold(True)
|
||||
@ -64,10 +63,23 @@ class AlertsManager(QtCore.QObject):
|
||||
if self.alertTab.location == 0:
|
||||
self.alertScreenPosition = 0
|
||||
else:
|
||||
self.alertScreenPosition = self.screen[u'size'].height() - self.alertHeight
|
||||
self.alertHeight = self.screen[u'size'].height() - self.alertScreenPosition
|
||||
self.parent.maindisplay.setAlertSize(self.alertScreenPosition, self.alertHeight)
|
||||
self.alertScreenPosition = self.screen[u'size'].height() \
|
||||
- self.alertHeight
|
||||
self.alertHeight = self.screen[u'size'].height() \
|
||||
- self.alertScreenPosition
|
||||
self.parent.maindisplay.setAlertSize(self.alertScreenPosition,\
|
||||
self.alertHeight)
|
||||
|
||||
def onAlertText(self, message):
|
||||
"""
|
||||
Called via a alerts_text event. Message is single element array
|
||||
containing text
|
||||
"""
|
||||
if message:
|
||||
self.displayAlert(message[0])
|
||||
else:
|
||||
self.displayAlert(u'')
|
||||
|
||||
def displayAlert(self, text=u''):
|
||||
"""
|
||||
Called from the Alert Tab to display an alert
|
||||
@ -76,12 +88,14 @@ class AlertsManager(QtCore.QObject):
|
||||
display text
|
||||
"""
|
||||
log.debug(u'display alert called %s' % text)
|
||||
self.parent.maindisplay.parent.StatusBar.showMessage(u'')
|
||||
if not self.screen:
|
||||
self.screenChanged()
|
||||
self.alertList.append(text)
|
||||
if self.timer_id != 0 or self.parent.maindisplay.mediaLoaded:
|
||||
self.parent.maindisplay.parent.StatusBar.showMessage(\
|
||||
self.trUtf8(u'Alert message created and delayed'))
|
||||
if self.timer_id != 0:
|
||||
Receiver.send_message(u'maindisplay_status_text',
|
||||
self.trUtf8(u'Alert message created and delayed'))
|
||||
return
|
||||
Receiver.send_message(u'maindisplay_status_text', u'')
|
||||
self.generateAlert()
|
||||
|
||||
def generateAlert(self):
|
||||
@ -113,6 +127,7 @@ class AlertsManager(QtCore.QObject):
|
||||
self.timer_id = self.startTimer(int(alertTab.timeout) * 1000)
|
||||
|
||||
def timerEvent(self, event):
|
||||
log.debug(u'timer event')
|
||||
if event.timerId() == self.timer_id:
|
||||
self.parent.maindisplay.addAlertImage(None, True)
|
||||
self.killTimer(self.timer_id)
|
||||
|
@ -25,17 +25,16 @@
|
||||
|
||||
from PyQt4 import QtCore, QtGui
|
||||
|
||||
from openlp.core.lib import SettingsTab, str_to_bool
|
||||
from openlp.plugins.alerts.lib.models import AlertItem
|
||||
from openlp.core.lib import SettingsTab
|
||||
|
||||
class AlertsTab(SettingsTab):
|
||||
"""
|
||||
AlertsTab is the alerts settings tab in the settings dialog.
|
||||
"""
|
||||
def __init__(self, parent, section=None):
|
||||
def __init__(self, parent):
|
||||
self.parent = parent
|
||||
self.manager = parent.manager
|
||||
SettingsTab.__init__(self, parent.name, section)
|
||||
SettingsTab.__init__(self, parent.name)
|
||||
|
||||
def setupUi(self):
|
||||
self.setObjectName(u'AlertsTab')
|
||||
@ -135,22 +134,6 @@ class AlertsTab(SettingsTab):
|
||||
QtGui.QSizePolicy.Expanding, QtGui.QSizePolicy.Minimum)
|
||||
self.LocationLayout.addItem(self.LocationSpacer)
|
||||
self.FontLayout.addWidget(self.LocationWidget)
|
||||
self.HistoryWidget = QtGui.QWidget(self.FontGroupBox)
|
||||
self.HistoryWidget.setObjectName(u'HistoryWidget')
|
||||
self.HistoryLayout = QtGui.QHBoxLayout(self.HistoryWidget)
|
||||
self.HistoryLayout.setSpacing(8)
|
||||
self.HistoryLayout.setMargin(0)
|
||||
self.HistoryLayout.setObjectName(u'HistoryLayout')
|
||||
self.HistoryLabel = QtGui.QLabel(self.HistoryWidget)
|
||||
self.HistoryLabel.setObjectName(u'HistoryLabel')
|
||||
self.HistoryLayout.addWidget(self.HistoryLabel)
|
||||
self.HistoryCheckBox = QtGui.QCheckBox(self.HistoryWidget)
|
||||
self.HistoryCheckBox.setObjectName(u'HistoryCheckBox')
|
||||
self.HistoryLayout.addWidget(self.HistoryCheckBox)
|
||||
self.HistorySpacer = QtGui.QSpacerItem(147, 20,
|
||||
QtGui.QSizePolicy.Expanding, QtGui.QSizePolicy.Minimum)
|
||||
self.HistoryLayout.addItem(self.HistorySpacer)
|
||||
self.FontLayout.addWidget(self.HistoryWidget)
|
||||
self.SlideLeftLayout.addWidget(self.FontGroupBox)
|
||||
self.SlideLeftSpacer = QtGui.QSpacerItem(20, 94,
|
||||
QtGui.QSizePolicy.Minimum, QtGui.QSizePolicy.Expanding)
|
||||
@ -187,48 +170,8 @@ class AlertsTab(SettingsTab):
|
||||
self.SlideRightSpacer = QtGui.QSpacerItem(20, 40,
|
||||
QtGui.QSizePolicy.Minimum, QtGui.QSizePolicy.Expanding)
|
||||
self.SlideRightLayout.addItem(self.SlideRightSpacer)
|
||||
self.layoutWidget = QtGui.QWidget(self)
|
||||
self.layoutWidget.setGeometry(QtCore.QRect(20, 10, 361, 251))
|
||||
self.layoutWidget.setObjectName(u'layoutWidget')
|
||||
self.verticalLayout_2 = QtGui.QVBoxLayout(self.layoutWidget)
|
||||
self.verticalLayout_2.setObjectName(u'verticalLayout_2')
|
||||
self.horizontalLayout_2 = QtGui.QHBoxLayout()
|
||||
self.horizontalLayout_2.setObjectName(u'horizontalLayout_2')
|
||||
self.AlertLineEdit = QtGui.QLineEdit(self.layoutWidget)
|
||||
self.AlertLineEdit.setObjectName(u'AlertLineEdit')
|
||||
self.horizontalLayout_2.addWidget(self.AlertLineEdit)
|
||||
self.verticalLayout_2.addLayout(self.horizontalLayout_2)
|
||||
self.horizontalLayout = QtGui.QHBoxLayout()
|
||||
self.horizontalLayout.setObjectName(u'horizontalLayout')
|
||||
self.AlertListWidget = QtGui.QListWidget(self.layoutWidget)
|
||||
self.AlertListWidget.setAlternatingRowColors(True)
|
||||
self.AlertListWidget.setObjectName(u'AlertListWidget')
|
||||
self.horizontalLayout.addWidget(self.AlertListWidget)
|
||||
self.verticalLayout = QtGui.QVBoxLayout()
|
||||
self.verticalLayout.setObjectName(u'verticalLayout')
|
||||
self.SaveButton = QtGui.QPushButton(self.layoutWidget)
|
||||
self.SaveButton.setObjectName(u'SaveButton')
|
||||
self.verticalLayout.addWidget(self.SaveButton)
|
||||
self.ClearButton = QtGui.QPushButton(self.layoutWidget)
|
||||
self.ClearButton.setObjectName(u'ClearButton')
|
||||
self.verticalLayout.addWidget(self.ClearButton)
|
||||
self.AddButton = QtGui.QPushButton(self.layoutWidget)
|
||||
self.AddButton.setObjectName(u'AddButton')
|
||||
self.verticalLayout.addWidget(self.AddButton)
|
||||
self.EditButton = QtGui.QPushButton(self.layoutWidget)
|
||||
self.EditButton.setObjectName(u'EditButton')
|
||||
self.verticalLayout.addWidget(self.EditButton)
|
||||
self.DeleteButton = QtGui.QPushButton(self.layoutWidget)
|
||||
self.DeleteButton.setObjectName(u'DeleteButton')
|
||||
self.verticalLayout.addWidget(self.DeleteButton)
|
||||
self.horizontalLayout.addLayout(self.verticalLayout)
|
||||
self.verticalLayout_2.addLayout(self.horizontalLayout)
|
||||
self.SlideRightLayout.addWidget(self.layoutWidget)
|
||||
self.AlertsLayout.addWidget(self.AlertRightColumn)
|
||||
# Signals and slots
|
||||
QtCore.QObject.connect(self.HistoryCheckBox,
|
||||
QtCore.SIGNAL(u'stateChanged(int)'),
|
||||
self.onHistoryCheckBoxChanged)
|
||||
QtCore.QObject.connect(self.BackgroundColorButton,
|
||||
QtCore.SIGNAL(u'pressed()'), self.onBackgroundColorButtonClicked)
|
||||
QtCore.QObject.connect(self.FontColorButton,
|
||||
@ -241,27 +184,6 @@ class AlertsTab(SettingsTab):
|
||||
QtCore.SIGNAL(u'valueChanged(int)'), self.onTimeoutSpinBoxChanged)
|
||||
QtCore.QObject.connect(self.FontSizeSpinBox,
|
||||
QtCore.SIGNAL(u'valueChanged(int)'), self.onFontSizeSpinBoxChanged)
|
||||
QtCore.QObject.connect(self.DeleteButton,
|
||||
QtCore.SIGNAL(u'clicked()'),
|
||||
self.onDeleteClick)
|
||||
QtCore.QObject.connect(self.ClearButton,
|
||||
QtCore.SIGNAL(u'clicked()'),
|
||||
self.onClearClick)
|
||||
QtCore.QObject.connect(self.EditButton,
|
||||
QtCore.SIGNAL(u'clicked()'),
|
||||
self.onEditClick)
|
||||
QtCore.QObject.connect(self.AddButton,
|
||||
QtCore.SIGNAL(u'clicked()'),
|
||||
self.onAddClick)
|
||||
QtCore.QObject.connect(self.SaveButton,
|
||||
QtCore.SIGNAL(u'clicked()'),
|
||||
self.onSaveClick)
|
||||
QtCore.QObject.connect(self.AlertListWidget,
|
||||
QtCore.SIGNAL(u'doubleClicked(QModelIndex)'),
|
||||
self.onItemSelected)
|
||||
QtCore.QObject.connect(self.AlertListWidget,
|
||||
QtCore.SIGNAL(u'clicked(QModelIndex)'),
|
||||
self.onItemSelected)
|
||||
|
||||
def retranslateUi(self):
|
||||
self.FontGroupBox.setTitle(self.trUtf8('Font'))
|
||||
@ -273,16 +195,10 @@ class AlertsTab(SettingsTab):
|
||||
self.TimeoutLabel.setText(self.trUtf8('Alert timeout:'))
|
||||
self.TimeoutSpinBox.setSuffix(self.trUtf8('s'))
|
||||
self.LocationLabel.setText(self.trUtf8('Location:'))
|
||||
self.HistoryLabel.setText(self.trUtf8('Keep History:'))
|
||||
self.PreviewGroupBox.setTitle(self.trUtf8('Preview'))
|
||||
self.FontPreview.setText(self.trUtf8('openlp.org'))
|
||||
self.LocationComboBox.setItemText(0, self.trUtf8('Top'))
|
||||
self.LocationComboBox.setItemText(1, self.trUtf8('Bottom'))
|
||||
self.SaveButton.setText(self.trUtf8('Save'))
|
||||
self.ClearButton.setText(self.trUtf8('Clear'))
|
||||
self.AddButton.setText(self.trUtf8('Add'))
|
||||
self.EditButton.setText(self.trUtf8('Edit'))
|
||||
self.DeleteButton.setText(self.trUtf8('Delete'))
|
||||
|
||||
def onBackgroundColorButtonClicked(self):
|
||||
self.bg_color = QtGui.QColorDialog.getColor(
|
||||
@ -297,12 +213,6 @@ class AlertsTab(SettingsTab):
|
||||
def onLocationComboBoxClicked(self, location):
|
||||
self.location = location
|
||||
|
||||
def onHistoryCheckBoxChanged(self, check_state):
|
||||
self.save_history = False
|
||||
# we have a set value convert to True/False
|
||||
if check_state == QtCore.Qt.Checked:
|
||||
self.save_history = True
|
||||
|
||||
def onFontColorButtonClicked(self):
|
||||
self.font_color = QtGui.QColorDialog.getColor(
|
||||
QtGui.QColor(self.font_color), self).name()
|
||||
@ -318,17 +228,20 @@ class AlertsTab(SettingsTab):
|
||||
self.updateDisplay()
|
||||
|
||||
def load(self):
|
||||
self.timeout = int(self.config.get_config(u'timeout', 5))
|
||||
self.font_color = unicode(
|
||||
self.config.get_config(u'font color', u'#ffffff'))
|
||||
self.font_size = int(self.config.get_config(u'font size', 40))
|
||||
self.bg_color = unicode(
|
||||
self.config.get_config(u'background color', u'#660000'))
|
||||
self.font_face = unicode(
|
||||
self.config.get_config(u'font face', QtGui.QFont().family()))
|
||||
self.location = int(self.config.get_config(u'location', 0))
|
||||
self.save_history = str_to_bool(
|
||||
self.config.get_config(u'save history', u'False'))
|
||||
settings = QtCore.QSettings()
|
||||
settings.beginGroup(self.settingsSection)
|
||||
self.timeout = settings.value(u'timeout', QtCore.QVariant(5)).toInt()[0]
|
||||
self.font_color = unicode(settings.value(
|
||||
u'font color', QtCore.QVariant(u'#ffffff')).toString())
|
||||
self.font_size = settings.value(
|
||||
u'font size', QtCore.QVariant(40)).toInt()[0]
|
||||
self.bg_color = unicode(settings.value(
|
||||
u'background color', QtCore.QVariant(u'#660000')).toString())
|
||||
self.font_face = unicode(settings.value(
|
||||
u'font face', QtCore.QVariant(QtGui.QFont().family())).toString())
|
||||
self.location = settings.value(
|
||||
u'location', QtCore.QVariant(0)).toInt()[0]
|
||||
settings.endGroup()
|
||||
self.FontSizeSpinBox.setValue(self.font_size)
|
||||
self.TimeoutSpinBox.setValue(self.timeout)
|
||||
self.FontColorButton.setStyleSheet(
|
||||
@ -336,91 +249,27 @@ class AlertsTab(SettingsTab):
|
||||
self.BackgroundColorButton.setStyleSheet(
|
||||
u'background-color: %s' % self.bg_color)
|
||||
self.LocationComboBox.setCurrentIndex(self.location)
|
||||
self.HistoryCheckBox.setChecked(self.save_history)
|
||||
font = QtGui.QFont()
|
||||
font.setFamily(self.font_face)
|
||||
self.FontComboBox.setCurrentFont(font)
|
||||
self.updateDisplay()
|
||||
self.loadList()
|
||||
|
||||
def loadList(self):
|
||||
self.AlertListWidget.clear()
|
||||
alerts = self.manager.get_all_alerts()
|
||||
for alert in alerts:
|
||||
item_name = QtGui.QListWidgetItem(alert.text)
|
||||
item_name.setData(
|
||||
QtCore.Qt.UserRole, QtCore.QVariant(alert.id))
|
||||
self.AlertListWidget.addItem(item_name)
|
||||
self.AddButton.setEnabled(True)
|
||||
self.ClearButton.setEnabled(False)
|
||||
self.SaveButton.setEnabled(False)
|
||||
self.EditButton.setEnabled(False)
|
||||
self.DeleteButton.setEnabled(False)
|
||||
|
||||
def onItemSelected(self):
|
||||
self.EditButton.setEnabled(True)
|
||||
self.DeleteButton.setEnabled(True)
|
||||
|
||||
def onDeleteClick(self):
|
||||
item = self.AlertListWidget.currentItem()
|
||||
if item:
|
||||
item_id = (item.data(QtCore.Qt.UserRole)).toInt()[0]
|
||||
self.parent.manager.delete_alert(item_id)
|
||||
row = self.AlertListWidget.row(item)
|
||||
self.AlertListWidget.takeItem(row)
|
||||
self.AddButton.setEnabled(True)
|
||||
self.SaveButton.setEnabled(False)
|
||||
self.DeleteButton.setEnabled(False)
|
||||
self.EditButton.setEnabled(False)
|
||||
|
||||
def onEditClick(self):
|
||||
item = self.AlertListWidget.currentItem()
|
||||
if item:
|
||||
self.item_id = (item.data(QtCore.Qt.UserRole)).toInt()[0]
|
||||
self.AlertLineEdit.setText(unicode(item.text()))
|
||||
self.AddButton.setEnabled(True)
|
||||
self.ClearButton.setEnabled(True)
|
||||
self.SaveButton.setEnabled(True)
|
||||
self.DeleteButton.setEnabled(True)
|
||||
self.EditButton.setEnabled(False)
|
||||
|
||||
def onClearClick(self):
|
||||
self.AlertLineEdit.setText(u'')
|
||||
self.AddButton.setEnabled(False)
|
||||
self.ClearButton.setEnabled(True)
|
||||
self.SaveButton.setEnabled(False)
|
||||
self.DeleteButton.setEnabled(False)
|
||||
self.EditButton.setEnabled(False)
|
||||
|
||||
def onAddClick(self):
|
||||
if len(self.AlertLineEdit.text()) == 0:
|
||||
QtGui.QMessageBox.information(self,
|
||||
self.trUtf8('Item selected to Add'),
|
||||
self.trUtf8('Missing data'))
|
||||
else:
|
||||
alert = AlertItem()
|
||||
alert.text = unicode(self.AlertLineEdit.text())
|
||||
self.manager.save_alert(alert)
|
||||
self.onClearClick()
|
||||
self.loadList()
|
||||
|
||||
def onSaveClick(self):
|
||||
alert = self.manager.get_alert(self.item_id)
|
||||
alert.text = unicode(self.AlertLineEdit.text())
|
||||
self.manager.save_alert(alert)
|
||||
self.onClearClick()
|
||||
self.loadList()
|
||||
|
||||
def save(self):
|
||||
settings = QtCore.QSettings()
|
||||
settings.beginGroup(self.settingsSection)
|
||||
self.font_face = self.FontComboBox.currentFont().family()
|
||||
self.config.set_config(u'background color', unicode(self.bg_color))
|
||||
self.config.set_config(u'font color', unicode(self.font_color))
|
||||
self.config.set_config(u'font size', unicode(self.font_size))
|
||||
self.config.set_config(u'font face', unicode(self.font_face))
|
||||
self.config.set_config(u'timeout', unicode(self.timeout))
|
||||
self.config.set_config(u'location',
|
||||
unicode(self.LocationComboBox.currentIndex()))
|
||||
self.config.set_config(u'save history', unicode(self.save_history))
|
||||
settings.setValue(u'background color', QtCore.QVariant(self.bg_color))
|
||||
settings.setValue(u'font color', QtCore.QVariant(self.font_color))
|
||||
settings.setValue(u'font size', QtCore.QVariant(self.font_size))
|
||||
settings.setValue(u'font face', QtCore.QVariant(self.font_face))
|
||||
settings.setValue(u'timeout', QtCore.QVariant(self.timeout))
|
||||
settings.setValue(u'location',
|
||||
QtCore.QVariant(self.LocationComboBox.currentIndex()))
|
||||
settings.endGroup()
|
||||
|
||||
def updateDisplay(self):
|
||||
font = QtGui.QFont()
|
@ -25,6 +25,9 @@
|
||||
|
||||
import logging
|
||||
|
||||
from PyQt4 import QtCore
|
||||
|
||||
from openlp.core.utils import AppLocation
|
||||
from openlp.plugins.alerts.lib.models import init_models, metadata, AlertItem
|
||||
|
||||
log = logging.getLogger(__name__)
|
||||
@ -36,27 +39,29 @@ class DBManager():
|
||||
"""
|
||||
log.info(u'Alerts DB loaded')
|
||||
|
||||
def __init__(self, config):
|
||||
def __init__(self):
|
||||
"""
|
||||
Creates the connection to the database, and creates the tables if they
|
||||
don't exist.
|
||||
"""
|
||||
self.config = config
|
||||
log.debug(u'Alerts Initialising')
|
||||
settings = QtCore.QSettings()
|
||||
settings.beginGroup(u'alerts')
|
||||
self.db_url = u''
|
||||
db_type = self.config.get_config(u'db type', u'sqlite')
|
||||
db_type = unicode(
|
||||
settings.value(u'db type', QtCore.QVariant(u'sqlite')).toString())
|
||||
if db_type == u'sqlite':
|
||||
self.db_url = u'sqlite:///%s/alerts.sqlite' % \
|
||||
self.config.get_data_path()
|
||||
AppLocation.get_section_data_path(u'alerts')
|
||||
else:
|
||||
self.db_url = u'%s://%s:%s@%s/%s' % \
|
||||
(db_type, self.config.get_config(u'db username'),
|
||||
self.config.get_config(u'db password'),
|
||||
self.config.get_config(u'db hostname'),
|
||||
self.config.get_config(u'db database'))
|
||||
self.db_url = u'%s://%s:%s@%s/%s' % (db_type,
|
||||
unicode(settings.value(u'db username').toString()),
|
||||
unicode(settings.value(u'db password').toString()),
|
||||
unicode(settings.value(u'db hostname').toString()),
|
||||
unicode(settings.value(u'db database').toString()))
|
||||
settings.endGroup()
|
||||
self.session = init_models(self.db_url)
|
||||
metadata.create_all(checkfirst=True)
|
||||
|
||||
log.debug(u'Alerts Initialised')
|
||||
|
||||
def get_all_alerts(self):
|
||||
|
@ -46,7 +46,7 @@ class BiblePlugin(Plugin):
|
||||
def initialise(self):
|
||||
log.info(u'bibles Initialising')
|
||||
if self.manager is None:
|
||||
self.manager = BibleManager(self, self.config)
|
||||
self.manager = BibleManager(self)
|
||||
Plugin.initialise(self)
|
||||
self.insert_toolbox_item()
|
||||
self.ImportBibleItem.setVisible(True)
|
||||
|
@ -24,6 +24,7 @@
|
||||
###############################################################################
|
||||
|
||||
from PyQt4 import QtCore, QtGui
|
||||
from openlp.core.lib import translate
|
||||
|
||||
class Ui_BibleImportWizard(object):
|
||||
def setupUi(self, BibleImportWizard):
|
||||
@ -307,47 +308,49 @@ class Ui_BibleImportWizard(object):
|
||||
QtCore.QMetaObject.connectSlotsByName(BibleImportWizard)
|
||||
|
||||
def retranslateUi(self, BibleImportWizard):
|
||||
BibleImportWizard.setWindowTitle(self.trUtf8('Bible Import Wizard'))
|
||||
BibleImportWizard.setWindowTitle(translate('ImportWizardForm', 'Bible Import Wizard'))
|
||||
self.TitleLabel.setText(
|
||||
u'<span style="font-size:14pt; font-weight:600;">%s</span>' % \
|
||||
self.trUtf8('Welcome to the Bible Import Wizard'))
|
||||
translate('ImportWizardForm', 'Welcome to the Bible Import Wizard'))
|
||||
self.InformationLabel.setText(
|
||||
self.trUtf8('This wizard will help you to import Bibles from a '
|
||||
translate('ImportWizardForm', 'This wizard will help you to import Bibles from a '
|
||||
'variety of formats. Click the next button below to start the '
|
||||
'process by selecting a format to import from.'))
|
||||
self.SelectPage.setTitle(self.trUtf8('Select Import Source'))
|
||||
self.SelectPage.setTitle(translate('ImportWizardForm', 'Select Import Source'))
|
||||
self.SelectPage.setSubTitle(
|
||||
self.trUtf8('Select the import format, and where to import from.'))
|
||||
self.FormatLabel.setText(self.trUtf8('Format:'))
|
||||
self.FormatComboBox.setItemText(0, self.trUtf8('OSIS'))
|
||||
self.FormatComboBox.setItemText(1, self.trUtf8('CSV'))
|
||||
self.FormatComboBox.setItemText(2, self.trUtf8('OpenSong'))
|
||||
self.FormatComboBox.setItemText(3, self.trUtf8('Web Download'))
|
||||
self.OsisLocationLabel.setText(self.trUtf8('File Location:'))
|
||||
self.BooksLocationLabel.setText(self.trUtf8('Books Location:'))
|
||||
self.VerseLocationLabel.setText(self.trUtf8('Verse Location:'))
|
||||
self.OpenSongFileLabel.setText(self.trUtf8('Bible Filename:'))
|
||||
self.LocationLabel.setText(self.trUtf8('Location:'))
|
||||
self.LocationComboBox.setItemText(0, self.trUtf8('Crosswalk'))
|
||||
self.LocationComboBox.setItemText(1, self.trUtf8('BibleGateway'))
|
||||
self.BibleLabel.setText(self.trUtf8('Bible:'))
|
||||
translate('ImportWizardForm', 'Select the import format, and where to import from.'))
|
||||
self.FormatLabel.setText(translate('ImportWizardForm', 'Format:'))
|
||||
self.FormatComboBox.setItemText(0, translate('ImportWizardForm', 'OSIS'))
|
||||
self.FormatComboBox.setItemText(1, translate('ImportWizardForm', 'CSV'))
|
||||
self.FormatComboBox.setItemText(2, translate('ImportWizardForm', 'OpenSong'))
|
||||
self.FormatComboBox.setItemText(3, translate('ImportWizardForm', 'Web Download'))
|
||||
self.OsisLocationLabel.setText(translate('ImportWizardForm', 'File Location:'))
|
||||
self.BooksLocationLabel.setText(translate('ImportWizardForm', 'Books Location:'))
|
||||
self.VerseLocationLabel.setText(translate('ImportWizardForm', 'Verse Location:'))
|
||||
self.OpenSongFileLabel.setText(translate('ImportWizardForm', 'Bible Filename:'))
|
||||
self.LocationLabel.setText(translate('ImportWizardForm', 'Location:'))
|
||||
self.LocationComboBox.setItemText(0, translate('ImportWizardForm', 'Crosswalk'))
|
||||
self.LocationComboBox.setItemText(1, translate('ImportWizardForm', 'BibleGateway'))
|
||||
self.BibleLabel.setText(translate('ImportWizardForm', 'Bible:'))
|
||||
self.WebDownloadTabWidget.setTabText(
|
||||
self.WebDownloadTabWidget.indexOf(self.DownloadOptionsTab),
|
||||
self.trUtf8('Download Options'))
|
||||
self.AddressLabel.setText(self.trUtf8('Server:'))
|
||||
self.UsernameLabel.setText(self.trUtf8('Username:'))
|
||||
self.PasswordLabel.setText(self.trUtf8('Password:'))
|
||||
translate('ImportWizardForm', 'Download Options'))
|
||||
self.AddressLabel.setText(translate('ImportWizardForm', 'Server:'))
|
||||
self.UsernameLabel.setText(translate('ImportWizardForm', 'Username:'))
|
||||
self.PasswordLabel.setText(translate('ImportWizardForm', 'Password:'))
|
||||
self.WebDownloadTabWidget.setTabText(
|
||||
self.WebDownloadTabWidget.indexOf(self.ProxyServerTab),
|
||||
self.trUtf8('Proxy Server (Optional)'))
|
||||
self.LicenseDetailsPage.setTitle(self.trUtf8('License Details'))
|
||||
translate('ImportWizardForm', 'Proxy Server (Optional)'))
|
||||
self.LicenseDetailsPage.setTitle(translate('ImportWizardForm', 'License Details'))
|
||||
self.LicenseDetailsPage.setSubTitle(
|
||||
self.trUtf8('Set up the Bible\'s license details.'))
|
||||
self.VersionNameLabel.setText(self.trUtf8('Version Name:'))
|
||||
self.CopyrightLabel.setText(self.trUtf8('Copyright:'))
|
||||
self.PermissionLabel.setText(self.trUtf8('Permission:'))
|
||||
self.ImportPage.setTitle(self.trUtf8('Importing'))
|
||||
translate('ImportWizardForm', 'Set up the Bible\'s license details.'))
|
||||
self.VersionNameLabel.setText(translate('ImportWizardForm', 'Version Name:'))
|
||||
self.CopyrightLabel.setText(translate('ImportWizardForm', 'Copyright:'))
|
||||
self.PermissionLabel.setText(translate('ImportWizardForm', 'Permission:'))
|
||||
self.ImportPage.setTitle(translate('ImportWizardForm', 'Importing'))
|
||||
self.ImportPage.setSubTitle(
|
||||
self.trUtf8('Please wait while your Bible is imported.'))
|
||||
self.ImportProgressLabel.setText(self.trUtf8('Ready.'))
|
||||
translate('ImportWizardForm', 'Please wait while your Bible is imported.'))
|
||||
self.ImportProgressLabel.setText(translate('ImportWizardForm', 'Ready.'))
|
||||
self.ImportProgressBar.setFormat(u'%p%')
|
||||
|
||||
|
||||
|
@ -31,7 +31,7 @@ import os.path
|
||||
from PyQt4 import QtCore, QtGui
|
||||
|
||||
from bibleimportwizard import Ui_BibleImportWizard
|
||||
from openlp.core.lib import Receiver
|
||||
from openlp.core.lib import Receiver, SettingsManager
|
||||
from openlp.core.utils import AppLocation, variant_to_unicode
|
||||
from openlp.plugins.bibles.lib.manager import BibleFormat
|
||||
|
||||
@ -59,16 +59,13 @@ class ImportWizardForm(QtGui.QWizard, Ui_BibleImportWizard):
|
||||
"""
|
||||
log.info(u'BibleImportForm loaded')
|
||||
|
||||
def __init__(self, parent, config, manager, bibleplugin):
|
||||
def __init__(self, parent, manager, bibleplugin):
|
||||
"""
|
||||
Instantiate the wizard, and run any extra setup we need to.
|
||||
|
||||
``parent``
|
||||
The QWidget-derived parent of the wizard.
|
||||
|
||||
``config``
|
||||
The configuration object for storing and retrieving settings.
|
||||
|
||||
``manager``
|
||||
The Bible manager.
|
||||
|
||||
@ -81,7 +78,6 @@ class ImportWizardForm(QtGui.QWizard, Ui_BibleImportWizard):
|
||||
self.finishButton = self.button(QtGui.QWizard.FinishButton)
|
||||
self.cancelButton = self.button(QtGui.QWizard.CancelButton)
|
||||
self.manager = manager
|
||||
self.config = config
|
||||
self.bibleplugin = bibleplugin
|
||||
self.manager.set_process_dialog(self)
|
||||
self.web_bible_list = {}
|
||||
@ -240,7 +236,7 @@ class ImportWizardForm(QtGui.QWizard, Ui_BibleImportWizard):
|
||||
"""
|
||||
log.debug('Cancel button pressed!')
|
||||
if self.currentId() == 3:
|
||||
Receiver.send_message(u'openlp_stop_bible_import')
|
||||
Receiver.send_message(u'bibles_stop_import')
|
||||
|
||||
def onCurrentIdChanged(self, id):
|
||||
if id == 3:
|
||||
@ -277,6 +273,8 @@ class ImportWizardForm(QtGui.QWizard, Ui_BibleImportWizard):
|
||||
u'license_permission', self.PermissionEdit)
|
||||
|
||||
def setDefaults(self):
|
||||
settings = QtCore.QSettings()
|
||||
settings.beginGroup(self.bibleplugin.settingsSection)
|
||||
self.setField(u'source_format', QtCore.QVariant(0))
|
||||
self.setField(u'osis_location', QtCore.QVariant(''))
|
||||
self.setField(u'csv_booksfile', QtCore.QVariant(''))
|
||||
@ -285,15 +283,17 @@ class ImportWizardForm(QtGui.QWizard, Ui_BibleImportWizard):
|
||||
self.setField(u'web_location', QtCore.QVariant(WebDownload.Crosswalk))
|
||||
self.setField(u'web_biblename', QtCore.QVariant(self.BibleComboBox))
|
||||
self.setField(u'proxy_server',
|
||||
QtCore.QVariant(self.config.get_config(u'proxy address', '')))
|
||||
settings.value(u'proxy address', QtCore.QVariant(u'')))
|
||||
self.setField(u'proxy_username',
|
||||
QtCore.QVariant(self.config.get_config(u'proxy username','')))
|
||||
settings.value(u'proxy username', QtCore.QVariant(u'')))
|
||||
self.setField(u'proxy_password',
|
||||
QtCore.QVariant(self.config.get_config(u'proxy password','')))
|
||||
settings.value(u'proxy password', QtCore.QVariant(u'')))
|
||||
self.setField(u'license_version', QtCore.QVariant(self.VersionNameEdit))
|
||||
self.setField(u'license_copyright', QtCore.QVariant(self.CopyrightEdit))
|
||||
self.setField(u'license_permission', QtCore.QVariant(self.PermissionEdit))
|
||||
self.setField(u'license_permission',
|
||||
QtCore.QVariant(self.PermissionEdit))
|
||||
self.onLocationComboBoxChanged(WebDownload.Crosswalk)
|
||||
settings.endGroup()
|
||||
|
||||
def loadWebBibles(self):
|
||||
"""
|
||||
@ -302,10 +302,10 @@ class ImportWizardForm(QtGui.QWizard, Ui_BibleImportWizard):
|
||||
#Load and store Crosswalk Bibles
|
||||
filepath = AppLocation.get_directory(AppLocation.PluginsDir)
|
||||
filepath = os.path.join(filepath, u'bibles', u'resources')
|
||||
fbibles = None
|
||||
try:
|
||||
self.web_bible_list[WebDownload.Crosswalk] = {}
|
||||
books_file = open(os.path.join(filepath, u'crosswalkbooks.csv'), 'r')
|
||||
books_file = open(
|
||||
os.path.join(filepath, u'crosswalkbooks.csv'), 'r')
|
||||
dialect = csv.Sniffer().sniff(books_file.read(1024))
|
||||
books_file.seek(0)
|
||||
books_reader = csv.reader(books_file, dialect)
|
||||
@ -345,16 +345,17 @@ class ImportWizardForm(QtGui.QWizard, Ui_BibleImportWizard):
|
||||
|
||||
def getFileName(self, title, editbox):
|
||||
filename = QtGui.QFileDialog.getOpenFileName(self, title,
|
||||
self.config.get_last_dir(1))
|
||||
SettingsManager.get_last_dir(self.bibleplugin.settingsSection, 1))
|
||||
if filename:
|
||||
editbox.setText(filename)
|
||||
self.config.set_last_dir(filename, 1)
|
||||
SettingsManager.set_last_dir(
|
||||
self.bibleplugin.settingsSection, filename, 1)
|
||||
|
||||
def incrementProgressBar(self, status_text):
|
||||
log.debug(u'IncrementBar %s', status_text)
|
||||
self.ImportProgressLabel.setText(status_text)
|
||||
self.ImportProgressBar.setValue(self.ImportProgressBar.value() + 1)
|
||||
Receiver.send_message(u'process_events')
|
||||
Receiver.send_message(u'openlp_process_events')
|
||||
|
||||
def preImport(self):
|
||||
self.finishButton.setVisible(False)
|
||||
@ -362,13 +363,14 @@ class ImportWizardForm(QtGui.QWizard, Ui_BibleImportWizard):
|
||||
self.ImportProgressBar.setMaximum(1188)
|
||||
self.ImportProgressBar.setValue(0)
|
||||
self.ImportProgressLabel.setText(self.trUtf8('Starting import...'))
|
||||
Receiver.send_message(u'process_events')
|
||||
Receiver.send_message(u'openlp_process_events')
|
||||
|
||||
def performImport(self):
|
||||
bible_type = self.field(u'source_format').toInt()[0]
|
||||
license_version = variant_to_unicode(self.field(u'license_version'))
|
||||
license_copyright = variant_to_unicode(self.field(u'license_copyright'))
|
||||
license_permission = variant_to_unicode(self.field(u'license_permission'))
|
||||
license_permission = variant_to_unicode(
|
||||
self.field(u'license_permission'))
|
||||
importer = None
|
||||
if bible_type == BibleFormat.OSIS:
|
||||
# Import an OSIS bible
|
||||
@ -424,4 +426,6 @@ class ImportWizardForm(QtGui.QWizard, Ui_BibleImportWizard):
|
||||
self.ImportProgressBar.setValue(self.ImportProgressBar.maximum())
|
||||
self.finishButton.setVisible(True)
|
||||
self.cancelButton.setVisible(False)
|
||||
Receiver.send_message(u'process_events')
|
||||
Receiver.send_message(u'openlp_process_events')
|
||||
|
||||
|
||||
|
@ -27,7 +27,7 @@ import logging
|
||||
|
||||
from PyQt4 import QtCore, QtGui
|
||||
|
||||
from openlp.core.lib import str_to_bool, Receiver, SettingsTab
|
||||
from openlp.core.lib import Receiver, SettingsTab
|
||||
|
||||
log = logging.getLogger(__name__)
|
||||
|
||||
@ -37,11 +37,11 @@ class BiblesTab(SettingsTab):
|
||||
"""
|
||||
log.info(u'Bible Tab loaded')
|
||||
|
||||
def __init__(self, title, section=None):
|
||||
def __init__(self, title):
|
||||
self.paragraph_style = True
|
||||
self.show_new_chapters = False
|
||||
self.display_style = 0
|
||||
SettingsTab.__init__(self, title, section)
|
||||
SettingsTab.__init__(self, title)
|
||||
|
||||
def setupUi(self):
|
||||
self.setObjectName(u'BiblesTab')
|
||||
@ -146,11 +146,12 @@ class BiblesTab(SettingsTab):
|
||||
self.BibleDualCheckBox, QtCore.SIGNAL(u'stateChanged(int)'),
|
||||
self.onBibleDualCheckBox)
|
||||
QtCore.QObject.connect(Receiver.get_receiver(),
|
||||
QtCore.SIGNAL(u'update_themes'), self.updateThemeList)
|
||||
QtCore.SIGNAL(u'theme_update_list'), self.updateThemeList)
|
||||
|
||||
def retranslateUi(self):
|
||||
self.VerseDisplayGroupBox.setTitle(self.trUtf8('Verse Display'))
|
||||
self.NewChaptersCheckBox.setText(self.trUtf8('Only show new chapter numbers'))
|
||||
self.NewChaptersCheckBox.setText(
|
||||
self.trUtf8('Only show new chapter numbers'))
|
||||
self.LayoutStyleLabel.setText(self.trUtf8('Layout Style:'))
|
||||
self.DisplayStyleLabel.setText(self.trUtf8('Display Style:'))
|
||||
self.BibleThemeLabel.setText(self.trUtf8('Bible Theme:'))
|
||||
@ -161,8 +162,8 @@ class BiblesTab(SettingsTab):
|
||||
self.DisplayStyleComboBox.setItemText(1, self.trUtf8('( and )'))
|
||||
self.DisplayStyleComboBox.setItemText(2, self.trUtf8('{ and }'))
|
||||
self.DisplayStyleComboBox.setItemText(3, self.trUtf8('[ and ]'))
|
||||
self.ChangeNoteLabel.setText(
|
||||
self.trUtf8('Note:\nChanges don\'t affect verses already in the service'))
|
||||
self.ChangeNoteLabel.setText(self.trUtf8(
|
||||
'Note:\nChanges don\'t affect verses already in the service'))
|
||||
self.BibleDualCheckBox.setText(self.trUtf8('Display Dual Bible Verses'))
|
||||
|
||||
def onBibleThemeComboBoxChanged(self):
|
||||
@ -187,29 +188,36 @@ class BiblesTab(SettingsTab):
|
||||
self.duel_bibles = True
|
||||
|
||||
def load(self):
|
||||
self.show_new_chapters = str_to_bool(
|
||||
self.config.get_config(u'display new chapter', u'False'))
|
||||
self.display_style = int(
|
||||
self.config.get_config(u'display brackets', u'0'))
|
||||
self.layout_style = int(
|
||||
self.config.get_config(u'verse layout style', u'0'))
|
||||
self.bible_theme = self.config.get_config(u'bible theme', u'0')
|
||||
self.duel_bibles = str_to_bool(
|
||||
self.config.get_config(u'dual bibles', u'True'))
|
||||
settings = QtCore.QSettings()
|
||||
settings.beginGroup(self.settingsSection)
|
||||
self.show_new_chapters = settings.value(
|
||||
u'display new chapter', QtCore.QVariant(False)).toBool()
|
||||
self.display_style = settings.value(
|
||||
u'display brackets', QtCore.QVariant(0)).toInt()[0]
|
||||
self.layout_style = settings.value(
|
||||
u'verse layout style', QtCore.QVariant(0)).toInt()[0]
|
||||
self.bible_theme = unicode(
|
||||
settings.value(u'bible theme', QtCore.QVariant(u'')).toString())
|
||||
self.duel_bibles = settings.value(
|
||||
u'dual bibles', QtCore.QVariant(True)).toBool()
|
||||
self.NewChaptersCheckBox.setChecked(self.show_new_chapters)
|
||||
self.DisplayStyleComboBox.setCurrentIndex(self.display_style)
|
||||
self.LayoutStyleComboBox.setCurrentIndex(self.layout_style)
|
||||
self.BibleDualCheckBox.setChecked(self.duel_bibles)
|
||||
settings.endGroup()
|
||||
|
||||
def save(self):
|
||||
self.config.set_config(
|
||||
u'display new chapter', unicode(self.show_new_chapters))
|
||||
self.config.set_config(
|
||||
u'display brackets', unicode(self.display_style))
|
||||
self.config.set_config(
|
||||
u'verse layout style', unicode(self.layout_style))
|
||||
self.config.set_config(u'dual bibles', unicode(self.duel_bibles))
|
||||
self.config.set_config(u'bible theme', unicode(self.bible_theme))
|
||||
settings = QtCore.QSettings()
|
||||
settings.beginGroup(self.settingsSection)
|
||||
settings.setValue(u'display new chapter',
|
||||
QtCore.QVariant(self.show_new_chapters))
|
||||
settings.setValue(u'display brackets',
|
||||
QtCore.QVariant(self.display_style))
|
||||
settings.setValue(u'verse layout style',
|
||||
QtCore.QVariant(self.layout_style))
|
||||
settings.setValue(u'dual bibles', QtCore.QVariant(self.duel_bibles))
|
||||
settings.setValue(u'bible theme', QtCore.QVariant(self.bible_theme))
|
||||
settings.endGroup()
|
||||
|
||||
def updateThemeList(self, theme_list):
|
||||
"""
|
||||
|
@ -52,7 +52,7 @@ class CSVBible(BibleDB):
|
||||
raise KeyError(u'You have to supply a file to import verses from.')
|
||||
self.versesfile = kwargs[u'versesfile']
|
||||
QtCore.QObject.connect(Receiver.get_receiver(),
|
||||
QtCore.SIGNAL(u'openlp_stop_bible_import'), self.stop_import)
|
||||
QtCore.SIGNAL(u'bibles_stop_import'), self.stop_import)
|
||||
|
||||
def stop_import(self):
|
||||
"""
|
||||
@ -77,7 +77,7 @@ class CSVBible(BibleDB):
|
||||
details = chardet.detect(line[1])
|
||||
self.create_book(unicode(line[1], details['encoding']),
|
||||
line[2], int(line[0]))
|
||||
Receiver.send_message(u'process_events')
|
||||
Receiver.send_message(u'openlp_process_events')
|
||||
except:
|
||||
log.exception(u'Loading books from file failed')
|
||||
success = False
|
||||
@ -105,7 +105,7 @@ class CSVBible(BibleDB):
|
||||
self.commit()
|
||||
self.create_verse(book.id, line[1], line[2],
|
||||
unicode(line[3], details['encoding']))
|
||||
Receiver.send_message(u'process_events')
|
||||
Receiver.send_message(u'openlp_process_events')
|
||||
self.commit()
|
||||
except:
|
||||
log.exception(u'Loading verses from file failed')
|
||||
@ -119,3 +119,4 @@ class CSVBible(BibleDB):
|
||||
else:
|
||||
return success
|
||||
|
||||
|
||||
|
@ -56,20 +56,14 @@ class BibleDB(QtCore.QObject):
|
||||
``name``
|
||||
The name of the database. This is also used as the file name for
|
||||
SQLite databases.
|
||||
|
||||
``config``
|
||||
The configuration object, passed in from the plugin.
|
||||
"""
|
||||
log.info(u'BibleDB loaded')
|
||||
QtCore.QObject.__init__(self)
|
||||
if u'path' not in kwargs:
|
||||
raise KeyError(u'Missing keyword argument "path".')
|
||||
if u'config' not in kwargs:
|
||||
raise KeyError(u'Missing keyword argument "config".')
|
||||
if u'name' not in kwargs and u'file' not in kwargs:
|
||||
raise KeyError(u'Missing keyword argument "name" or "file".')
|
||||
self.stop_import_flag = False
|
||||
self.config = kwargs[u'config']
|
||||
if u'name' in kwargs:
|
||||
self.name = kwargs[u'name']
|
||||
if not isinstance(self.name, unicode):
|
||||
@ -79,16 +73,20 @@ class BibleDB(QtCore.QObject):
|
||||
self.file = kwargs[u'file']
|
||||
self.db_file = os.path.join(kwargs[u'path'], self.file)
|
||||
log.debug(u'Load bible %s on path %s', self.file, self.db_file)
|
||||
db_type = self.config.get_config(u'db type', u'sqlite')
|
||||
settings = QtCore.QSettings()
|
||||
settings.beginGroup(u'bibles')
|
||||
db_type = unicode(
|
||||
settings.value(u'db type', QtCore.QVariant(u'sqlite')).toString())
|
||||
db_url = u''
|
||||
if db_type == u'sqlite':
|
||||
db_url = u'sqlite:///' + self.db_file
|
||||
else:
|
||||
db_url = u'%s://%s:%s@%s/%s' % \
|
||||
(db_type, self.config.get_config(u'db username'),
|
||||
self.config.get_config(u'db password'),
|
||||
self.config.get_config(u'db hostname'),
|
||||
self.config.get_config(u'db database'))
|
||||
db_url = u'%s://%s:%s@%s/%s' % (db_type,
|
||||
unicode(settings.value(u'db username').toString()),
|
||||
unicode(settings.value(u'db password').toString()),
|
||||
unicode(settings.value(u'db hostname').toString()),
|
||||
unicode(settings.value(u'db database').toString()))
|
||||
settings.endGroup()
|
||||
self.metadata, self.session = init_models(db_url)
|
||||
self.metadata.create_all(checkfirst=True)
|
||||
if u'file' in kwargs:
|
||||
@ -113,7 +111,7 @@ class BibleDB(QtCore.QObject):
|
||||
``old_filename``
|
||||
The "dirty" file name or version name.
|
||||
"""
|
||||
if not isinstance(old_filename, unicode):
|
||||
if not isinstance(old_filename, unicode):
|
||||
old_filename = unicode(old_filename, u'utf-8')
|
||||
old_filename = re.sub(r'[^\w]+', u'_', old_filename).strip(u'_')
|
||||
return old_filename + u'.sqlite'
|
||||
|
@ -203,9 +203,9 @@ class BGExtract(BibleCommon):
|
||||
# Let's get the page, and then open it in BeautifulSoup, so as to
|
||||
# attempt to make "easy" work of bad HTML.
|
||||
page = urllib2.urlopen(urlstring)
|
||||
Receiver.send_message(u'process_events')
|
||||
Receiver.send_message(u'openlp_process_events')
|
||||
soup = BeautifulSoup(page)
|
||||
Receiver.send_message(u'process_events')
|
||||
Receiver.send_message(u'openlp_process_events')
|
||||
verses = soup.find(u'div', u'result-text-style-normal')
|
||||
verse_number = 0
|
||||
verse_list = {0: u''}
|
||||
@ -213,7 +213,7 @@ class BGExtract(BibleCommon):
|
||||
# This is a PERFECT example of opening the Cthulu tag!
|
||||
# O Bible Gateway, why doth ye such horrific HTML produce?
|
||||
for verse in verses:
|
||||
Receiver.send_message(u'process_events')
|
||||
Receiver.send_message(u'openlp_process_events')
|
||||
if isinstance(verse, Tag) and verse.name == u'div' and filter(lambda a: a[0] == u'class', verse.attrs)[0][1] == u'footnotes':
|
||||
break
|
||||
if isinstance(verse, Tag) and verse.name == u'sup' and filter(lambda a: a[0] == u'class', verse.attrs)[0][1] != u'versenum':
|
||||
@ -222,7 +222,7 @@ class BGExtract(BibleCommon):
|
||||
continue
|
||||
if isinstance(verse, Tag) and (verse.name == u'p' or verse.name == u'font') and verse.contents:
|
||||
for item in verse.contents:
|
||||
Receiver.send_message(u'process_events')
|
||||
Receiver.send_message(u'openlp_process_events')
|
||||
if isinstance(item, Tag) and (item.name == u'h4' or item.name == u'h5'):
|
||||
continue
|
||||
if isinstance(item, Tag) and item.name == u'sup' and filter(lambda a: a[0] == u'class', item.attrs)[0][1] != u'versenum':
|
||||
@ -235,7 +235,7 @@ class BGExtract(BibleCommon):
|
||||
continue
|
||||
if isinstance(item, Tag) and item.name == u'font':
|
||||
for subitem in item.contents:
|
||||
Receiver.send_message(u'process_events')
|
||||
Receiver.send_message(u'openlp_process_events')
|
||||
if isinstance(subitem, Tag) and subitem.name == u'sup' and filter(lambda a: a[0] == u'class', subitem.attrs)[0][1] != u'versenum':
|
||||
continue
|
||||
if isinstance(subitem, Tag) and subitem.name == u'p' and not subitem.contents:
|
||||
@ -294,37 +294,37 @@ class CWExtract(BibleCommon):
|
||||
(version, urlbookname.lower(), chapter)
|
||||
log.debug(u'URL: %s', chapter_url)
|
||||
page = urllib2.urlopen(chapter_url)
|
||||
Receiver.send_message(u'process_events')
|
||||
Receiver.send_message(u'openlp_process_events')
|
||||
if not page:
|
||||
return None
|
||||
soup = BeautifulSoup(page)
|
||||
Receiver.send_message(u'process_events')
|
||||
Receiver.send_message(u'openlp_process_events')
|
||||
htmlverses = soup.findAll(u'span', u'versetext')
|
||||
verses = {}
|
||||
reduce_spaces = re.compile(r'[ ]{2,}')
|
||||
fix_punctuation = re.compile(r'[ ]+([.,;])')
|
||||
for verse in htmlverses:
|
||||
Receiver.send_message(u'process_events')
|
||||
Receiver.send_message(u'openlp_process_events')
|
||||
versenumber = int(verse.contents[0].contents[0])
|
||||
versetext = u''
|
||||
for part in verse.contents:
|
||||
Receiver.send_message(u'process_events')
|
||||
Receiver.send_message(u'openlp_process_events')
|
||||
if isinstance(part, NavigableString):
|
||||
versetext = versetext + part
|
||||
elif part and part.attrMap and \
|
||||
(part.attrMap[u'class'] == u'WordsOfChrist' or \
|
||||
part.attrMap[u'class'] == u'strongs'):
|
||||
for subpart in part.contents:
|
||||
Receiver.send_message(u'process_events')
|
||||
Receiver.send_message(u'openlp_process_events')
|
||||
if isinstance(subpart, NavigableString):
|
||||
versetext = versetext + subpart
|
||||
elif subpart and subpart.attrMap and \
|
||||
subpart.attrMap[u'class'] == u'strongs':
|
||||
for subsub in subpart.contents:
|
||||
Receiver.send_message(u'process_events')
|
||||
Receiver.send_message(u'openlp_process_events')
|
||||
if isinstance(subsub, NavigableString):
|
||||
versetext = versetext + subsub
|
||||
Receiver.send_message(u'process_events')
|
||||
Receiver.send_message(u'openlp_process_events')
|
||||
# Fix up leading and trailing spaces, multiple spaces, and spaces
|
||||
# between text and , and .
|
||||
versetext = versetext.strip(u'\n\r\t ')
|
||||
@ -415,14 +415,14 @@ class HTTPBible(BibleDB):
|
||||
if not db_book:
|
||||
book_details = self.lookup_book(book)
|
||||
if not book_details:
|
||||
Receiver.send_message(u'bible_nobook')
|
||||
Receiver.send_message(u'bibles_nobook')
|
||||
return []
|
||||
db_book = self.create_book(book_details[u'name'],
|
||||
book_details[u'abbreviation'], book_details[u'testament_id'])
|
||||
book = db_book.name
|
||||
if BibleDB.get_verse_count(self, book, reference[1]) == 0:
|
||||
Receiver.send_message(u'bible_showprogress')
|
||||
Receiver.send_message(u'process_events')
|
||||
Receiver.send_message(u'bibles_showprogress')
|
||||
Receiver.send_message(u'openlp_process_events')
|
||||
search_results = self.get_chapter(self.name, book, reference[1])
|
||||
if search_results and search_results.has_verselist():
|
||||
## We have found a book of the bible lets check to see
|
||||
@ -430,14 +430,14 @@ class HTTPBible(BibleDB):
|
||||
## we get a correct book. For example it is possible
|
||||
## to request ac and get Acts back.
|
||||
bookname = search_results.get_book()
|
||||
Receiver.send_message(u'process_events')
|
||||
Receiver.send_message(u'openlp_process_events')
|
||||
# check to see if book/chapter exists
|
||||
db_book = self.get_book(bookname)
|
||||
self.create_chapter(db_book.id, search_results.get_chapter(),
|
||||
search_results.get_verselist())
|
||||
Receiver.send_message(u'process_events')
|
||||
Receiver.send_message(u'bible_hideprogress')
|
||||
Receiver.send_message(u'process_events')
|
||||
Receiver.send_message(u'openlp_process_events')
|
||||
Receiver.send_message(u'bibles_hideprogress')
|
||||
Receiver.send_message(u'openlp_process_events')
|
||||
return BibleDB.get_verses(self, reference_list)
|
||||
|
||||
def get_chapter(self, version, book, chapter):
|
||||
@ -496,4 +496,3 @@ class HTTPBible(BibleDB):
|
||||
The hostname or IP address of the proxy server.
|
||||
"""
|
||||
self.proxy_server = server
|
||||
|
||||
|
@ -25,6 +25,11 @@
|
||||
|
||||
import logging
|
||||
|
||||
from PyQt4 import QtCore
|
||||
|
||||
from openlp.core.lib import SettingsManager
|
||||
from openlp.core.utils import AppLocation
|
||||
|
||||
from common import parse_reference
|
||||
from opensong import OpenSongBible
|
||||
from osis import OSISBible
|
||||
@ -94,25 +99,24 @@ class BibleManager(object):
|
||||
"""
|
||||
log.info(u'Bible manager loaded')
|
||||
|
||||
def __init__(self, parent, config):
|
||||
def __init__(self, parent):
|
||||
"""
|
||||
Finds all the bibles defined for the system and creates an interface
|
||||
object for each bible containing connection information. Throws
|
||||
Exception if no Bibles are found.
|
||||
|
||||
Init confirms the bible exists and stores the database path.
|
||||
|
||||
``config``
|
||||
The plugin's configuration object.
|
||||
"""
|
||||
log.debug(u'Bible Initialising')
|
||||
self.config = config
|
||||
self.parent = parent
|
||||
self.settingsSection = u'bibles'
|
||||
self.web = u'Web'
|
||||
self.db_cache = None
|
||||
self.path = self.config.get_data_path()
|
||||
self.proxy_name = self.config.get_config(u'proxy name')
|
||||
self.suffix = u'sqlite'
|
||||
self.path = AppLocation.get_section_data_path(self.settingsSection)
|
||||
self.proxy_name = unicode(
|
||||
QtCore.QSettings().value(self.settingsSection + u'/proxy name',
|
||||
QtCore.QVariant(u'')).toString())
|
||||
self.suffix = u'.sqlite'
|
||||
self.import_wizard = None
|
||||
self.reload_bibles()
|
||||
self.media = None
|
||||
@ -124,23 +128,23 @@ class BibleManager(object):
|
||||
BibleDB class.
|
||||
"""
|
||||
log.debug(u'Reload bibles')
|
||||
files = self.config.get_files(self.suffix)
|
||||
files = SettingsManager.get_files(self.settingsSection, self.suffix)
|
||||
log.debug(u'Bible Files %s', files)
|
||||
self.db_cache = {}
|
||||
for filename in files:
|
||||
bible = BibleDB(self.parent, path=self.path, file=filename,
|
||||
config=self.config)
|
||||
bible = BibleDB(self.parent, path=self.path, file=filename)
|
||||
name = bible.get_name()
|
||||
log.debug(u'Bible Name: "%s"', name)
|
||||
self.db_cache[name] = bible
|
||||
# look to see if lazy load bible exists and get create getter.
|
||||
source = self.db_cache[name].get_meta(u'download source')
|
||||
if source:
|
||||
download_name = self.db_cache[name].get_meta(u'download name').value
|
||||
download_name = \
|
||||
self.db_cache[name].get_meta(u'download name').value
|
||||
meta_proxy = self.db_cache[name].get_meta(u'proxy url')
|
||||
web_bible = HTTPBible(self.parent, path=self.path,
|
||||
file=filename, config=self.config,
|
||||
download_source=source.value, download_name=download_name)
|
||||
file=filename, download_source=source.value,
|
||||
download_name=download_name)
|
||||
if meta_proxy:
|
||||
web_bible.set_proxy_server(meta_proxy.value)
|
||||
self.db_cache[name] = web_bible
|
||||
@ -167,7 +171,6 @@ class BibleManager(object):
|
||||
"""
|
||||
class_ = BibleFormat.get_class(type)
|
||||
kwargs['path'] = self.path
|
||||
kwargs['config'] = self.config
|
||||
importer = class_(self.parent, **kwargs)
|
||||
name = importer.register(self.import_wizard)
|
||||
self.db_cache[name] = importer
|
||||
@ -208,7 +211,8 @@ class BibleManager(object):
|
||||
Returns all the number of verses for a given
|
||||
book and chapterMaxBibleBookVerses
|
||||
"""
|
||||
log.debug(u'BibleManager.get_verse_count("%s", "%s", %s)', bible, book, chapter)
|
||||
log.debug(u'BibleManager.get_verse_count("%s", "%s", %s)',
|
||||
bible, book, chapter)
|
||||
return self.db_cache[bible].get_verse_count(book, chapter)
|
||||
|
||||
def get_verses(self, bible, versetext):
|
||||
@ -260,4 +264,3 @@ class BibleManager(object):
|
||||
if bible == name:
|
||||
return True
|
||||
return False
|
||||
|
||||
|
@ -28,15 +28,15 @@ import time
|
||||
|
||||
from PyQt4 import QtCore, QtGui
|
||||
|
||||
from openlp.core.lib import MediaManagerItem, Receiver, str_to_bool, \
|
||||
BaseListWithDnD
|
||||
from openlp.core.lib import MediaManagerItem, Receiver, BaseListWithDnD, \
|
||||
ItemCapabilities
|
||||
from openlp.plugins.bibles.forms import ImportWizardForm
|
||||
|
||||
log = logging.getLogger(__name__)
|
||||
|
||||
class BibleListView(BaseListWithDnD):
|
||||
"""
|
||||
Drag and drop capable list for Bibles.
|
||||
Custom list view descendant, required for drag and drop.
|
||||
"""
|
||||
def __init__(self, parent=None):
|
||||
self.PluginName = u'Bibles'
|
||||
@ -54,17 +54,15 @@ class BibleMediaItem(MediaManagerItem):
|
||||
|
||||
def __init__(self, parent, icon, title):
|
||||
self.PluginNameShort = u'Bible'
|
||||
self.ConfigSection = title
|
||||
self.IconPath = u'songs/song'
|
||||
self.ListViewWithDnD_class = BibleListView
|
||||
self.servicePath = None
|
||||
self.lastReference = []
|
||||
self.addToServiceItem = True
|
||||
MediaManagerItem.__init__(self, parent, icon, title)
|
||||
# place to store the search results
|
||||
self.search_results = {}
|
||||
QtCore.QObject.connect(Receiver.get_receiver(),
|
||||
QtCore.SIGNAL(u'openlpreloadbibles'), self.reloadBibles)
|
||||
QtCore.SIGNAL(u'bibles_load_list'), self.reloadBibles)
|
||||
|
||||
def _decodeQtObject(self, listobj, key):
|
||||
obj = listobj[QtCore.QString(key)]
|
||||
@ -258,11 +256,11 @@ class BibleMediaItem(MediaManagerItem):
|
||||
QtCore.QObject.connect(self.QuickSearchEdit,
|
||||
QtCore.SIGNAL(u'returnPressed()'), self.onQuickSearchButton)
|
||||
QtCore.QObject.connect(Receiver.get_receiver(),
|
||||
QtCore.SIGNAL(u'bible_showprogress'), self.onSearchProgressShow)
|
||||
QtCore.SIGNAL(u'bibles_showprogress'), self.onSearchProgressShow)
|
||||
QtCore.QObject.connect(Receiver.get_receiver(),
|
||||
QtCore.SIGNAL(u'bible_hideprogress'), self.onSearchProgressHide)
|
||||
QtCore.SIGNAL(u'bibles_hideprogress'), self.onSearchProgressHide)
|
||||
QtCore.QObject.connect(Receiver.get_receiver(),
|
||||
QtCore.SIGNAL(u'bible_nobook'), self.onNoBookFound)
|
||||
QtCore.SIGNAL(u'bibles_nobook'), self.onNoBookFound)
|
||||
|
||||
def addListViewToToolBar(self):
|
||||
MediaManagerItem.addListViewToToolBar(self)
|
||||
@ -277,8 +275,8 @@ class BibleMediaItem(MediaManagerItem):
|
||||
self.SearchProgress.setObjectName(u'SearchProgress')
|
||||
|
||||
def configUpdated(self):
|
||||
if str_to_bool(
|
||||
self.parent.config.get_config(u'dual bibles', u'False')):
|
||||
if QtCore.QSettings().value(self.settingsSection + u'/dual bibles',
|
||||
QtCore.QVariant(False)).toBool():
|
||||
self.AdvancedSecondBibleLabel.setVisible(True)
|
||||
self.AdvancedSecondBibleComboBox.setVisible(True)
|
||||
self.QuickSecondVersionLabel.setVisible(True)
|
||||
@ -323,7 +321,7 @@ class BibleMediaItem(MediaManagerItem):
|
||||
def setQuickMessage(self, text):
|
||||
self.QuickMessage.setText(text)
|
||||
self.AdvancedMessage.setText(text)
|
||||
Receiver.send_message(u'process_events')
|
||||
Receiver.send_message(u'openlp_process_events')
|
||||
#minor delay to get the events processed
|
||||
time.sleep(0.1)
|
||||
|
||||
@ -339,13 +337,14 @@ class BibleMediaItem(MediaManagerItem):
|
||||
# load bibles into the combo boxes
|
||||
first = True
|
||||
for bible in bibles:
|
||||
self.QuickVersionComboBox.addItem(bible)
|
||||
self.QuickSecondBibleComboBox.addItem(bible)
|
||||
self.AdvancedVersionComboBox.addItem(bible)
|
||||
self.AdvancedSecondBibleComboBox.addItem(bible)
|
||||
if first:
|
||||
first = False
|
||||
self.initialiseBible(bible)
|
||||
if bible:
|
||||
self.QuickVersionComboBox.addItem(bible)
|
||||
self.QuickSecondBibleComboBox.addItem(bible)
|
||||
self.AdvancedVersionComboBox.addItem(bible)
|
||||
self.AdvancedSecondBibleComboBox.addItem(bible)
|
||||
if first:
|
||||
first = False
|
||||
self.initialiseBible(bible)
|
||||
|
||||
def onListViewResize(self, width, height):
|
||||
self.SearchProgress.setGeometry(self.ListView.geometry().x(),
|
||||
@ -354,7 +353,7 @@ class BibleMediaItem(MediaManagerItem):
|
||||
|
||||
def onSearchProgressShow(self):
|
||||
self.SearchProgress.setVisible(True)
|
||||
Receiver.send_message(u'process_events')
|
||||
Receiver.send_message(u'openlp_process_events')
|
||||
#self.SearchProgress.setMinimum(0)
|
||||
#self.SearchProgress.setMaximum(2)
|
||||
#self.SearchProgress.setValue(1)
|
||||
@ -382,7 +381,7 @@ class BibleMediaItem(MediaManagerItem):
|
||||
self.AdvancedBookComboBox.itemData(item).toInt()[0])
|
||||
|
||||
def onImportClick(self):
|
||||
self.bibleimportform = ImportWizardForm(self, self.parent.config,
|
||||
self.bibleimportform = ImportWizardForm(self,
|
||||
self.parent.manager, self.parent)
|
||||
self.bibleimportform.exec_()
|
||||
self.reloadBibles()
|
||||
@ -440,7 +439,7 @@ class BibleMediaItem(MediaManagerItem):
|
||||
if self.search_results:
|
||||
self.displayResults(bible)
|
||||
|
||||
def generateSlideData(self, service_item):
|
||||
def generateSlideData(self, service_item, item=None):
|
||||
log.debug(u'generating slide data')
|
||||
items = self.ListView.selectedIndexes()
|
||||
if len(items) == 0:
|
||||
@ -449,7 +448,9 @@ class BibleMediaItem(MediaManagerItem):
|
||||
raw_slides = []
|
||||
raw_footer = []
|
||||
bible_text = u''
|
||||
service_item.auto_preview_allowed = True
|
||||
service_item.add_capability(ItemCapabilities.AllowsPreview)
|
||||
service_item.add_capability(ItemCapabilities.AllowsLoop)
|
||||
service_item.add_capability(ItemCapabilities.AllowsAdditions)
|
||||
#If we want to use a 2nd translation / version
|
||||
bible2 = u''
|
||||
if self.SearchTabWidget.currentIndex() == 0:
|
||||
@ -518,7 +519,7 @@ class BibleMediaItem(MediaManagerItem):
|
||||
else:
|
||||
service_item.theme = self.parent.settings_tab.bible_theme
|
||||
#if we are verse per slide we have already been added
|
||||
if self.parent.settings_tab.layout_style != 0:
|
||||
if self.parent.settings_tab.layout_style != 0 and not bible2:
|
||||
raw_slides.append(bible_text)
|
||||
for slide in raw_slides:
|
||||
service_item.add_from_text(slide[:30], slide)
|
||||
@ -608,4 +609,4 @@ class BibleMediaItem(MediaManagerItem):
|
||||
|
||||
def searchByReference(self, bible, search):
|
||||
log.debug(u'searchByReference %s, %s', bible, search)
|
||||
self.search_results = self.parent.manager.get_verses(bible, search)
|
||||
self.search_results = self.parent.manager.get_verses(bible, search)
|
||||
|
@ -49,7 +49,7 @@ class OpenSongBible(BibleDB):
|
||||
raise KeyError(u'You have to supply a file name to import from.')
|
||||
self.filename = kwargs['filename']
|
||||
QtCore.QObject.connect(Receiver.get_receiver(),
|
||||
QtCore.SIGNAL(u'openlp_stop_bible_import'), self.stop_import)
|
||||
QtCore.SIGNAL(u'bibles_stop_import'), self.stop_import)
|
||||
|
||||
def stop_import(self):
|
||||
"""
|
||||
@ -92,7 +92,7 @@ class OpenSongBible(BibleDB):
|
||||
int(verse.attrib[u'n']),
|
||||
unicode(verse.text)
|
||||
)
|
||||
Receiver.send_message(u'process_events')
|
||||
Receiver.send_message(u'openlp_process_events')
|
||||
self.wizard.incrementProgressBar(
|
||||
QtCore.QString('%s %s %s' % (self.trUtf8('Importing'),\
|
||||
db_book.name, chapter.attrib[u'n'])))
|
||||
@ -108,3 +108,5 @@ class OpenSongBible(BibleDB):
|
||||
return False
|
||||
else:
|
||||
return success
|
||||
|
||||
|
||||
|