diff --git a/openlp/core/lib/htmlbuilder.py b/openlp/core/lib/htmlbuilder.py
index e7c6c7ddd..62395b4ab 100644
--- a/openlp/core/lib/htmlbuilder.py
+++ b/openlp/core/lib/htmlbuilder.py
@@ -66,6 +66,7 @@ body {
#image {
z-index:2;
}
+%s
#video1 {
z-index:3;
}
@@ -98,97 +99,8 @@ sup {
-
-
-
+%s
%s
@@ -397,7 +242,7 @@ sup {
"""
-def build_html(item, screen, alert, islive, background, image=None):
+def build_html(item, screen, alert, islive, background, plugins=None, image=None):
"""
Build the full web paged structure for display
@@ -416,6 +261,9 @@ def build_html(item, screen, alert, islive, background, image=None):
``background``
Theme background image - bytes
+ ``plugins``
+ access to the plugins
+
``image``
Image media item - bytes
"""
@@ -434,14 +282,25 @@ def build_html(item, screen, alert, islive, background, image=None):
image_src = u'src="data:image/png;base64,%s"' % image
else:
image_src = u'style="display:none;"'
+ plugin_css = u''
+ plugin_js = u''
+ plugin_html = u''
+ if plugins:
+ for plugin in plugins:
+ plugin_css += plugin.display_css()
+ plugin_js += plugin.display_javascript()
+ plugin_html += plugin.display_html()
html = HTMLSRC % (build_background_css(item, width, height),
width, height,
+ plugin_css,
build_alert_css(alert, width),
build_footer_css(item, height),
build_lyrics_css(item, webkitvers),
u'true' if theme and theme.display_slide_transition and islive \
else u'false',
+ plugin_js,
bgimage_src, image_src,
+ plugin_html,
build_lyrics_html(item, webkitvers))
return html
diff --git a/openlp/core/lib/plugin.py b/openlp/core/lib/plugin.py
index d92464cdc..e81aae46d 100644
--- a/openlp/core/lib/plugin.py
+++ b/openlp/core/lib/plugin.py
@@ -374,3 +374,21 @@ class Plugin(QtCore.QObject):
after this has been set.
"""
self.textStrings[name] = {u'title': title, u'tooltip': tooltip}
+
+ def display_css(self):
+ """
+ Add css style sheets to htmlbuilder
+ """
+ return u''
+
+ def display_javascript(self):
+ """
+ Add javascript functions to htmlbuilder
+ """
+ return u''
+
+ def display_html(self):
+ """
+ Add html code to htmlbuilder
+ """
+ return u''
diff --git a/openlp/core/ui/maindisplay.py b/openlp/core/ui/maindisplay.py
index 5987764b6..d054f78bd 100644
--- a/openlp/core/ui/maindisplay.py
+++ b/openlp/core/ui/maindisplay.py
@@ -56,18 +56,22 @@ class Display(QtGui.QGraphicsView):
"""
Set up and build the preview screen
"""
+# self.setGeometry(0, 0,
+# self.parent().width(), self.parent().height())
self.webView = QtWebKit.QWebView(self)
self.webView.setGeometry(0, 0,
self.parent().width(), self.parent().height())
- self.webView.settings().setAttribute(QtWebKit.QWebSettings.PluginsEnabled, True)
+ self.webView.settings().setAttribute(
+ QtWebKit.QWebSettings.PluginsEnabled, True)
self.page = self.webView.page()
self.frame = self.page.mainFrame()
screen = {}
screen[u'size'] = self.size()
serviceItem = ServiceItem()
self.webView.setHtml(build_html(serviceItem, screen,
- None, None, None))
+ None, None, None, self.controller.parent().pluginManager.plugins))
self.webView.hide()
+ #self.hide()
class MainDisplay(QtGui.QGraphicsView):
"""
@@ -158,7 +162,8 @@ class MainDisplay(QtGui.QGraphicsView):
serviceItem = ServiceItem()
serviceItem.bg_image_bytes = image_to_byte(self.initialFrame)
self.webView.setHtml(build_html(serviceItem, self.screen,
- self.alertTab, self.isLive, None))
+ self.alertTab, self.isLive, None,
+ self.controller.parent().pluginManager.plugins))
self.__hideMouse()
# To display or not to display?
if not self.screen[u'primary']:
@@ -350,7 +355,7 @@ class MainDisplay(QtGui.QGraphicsView):
else:
image_bytes = None
html = build_html(self.serviceItem, self.screen, self.alertTab,
- self.isLive, background, image_bytes)
+ self.isLive, background, self.controller.parent().pluginManager.plugins, image_bytes)
log.debug(u'buildHtml - pre setHtml')
self.webView.setHtml(html)
log.debug(u'buildHtml - post setHtml')
diff --git a/openlp/core/ui/slidecontroller.py b/openlp/core/ui/slidecontroller.py
index 678f16cf7..e5420f0fe 100644
--- a/openlp/core/ui/slidecontroller.py
+++ b/openlp/core/ui/slidecontroller.py
@@ -62,7 +62,6 @@ class SlideController(QtGui.QWidget):
self.screens = ScreenList.get_instance()
self.ratio = float(self.screens.current[u'size'].width()) / \
float(self.screens.current[u'size'].height())
- #self.display = None#MainDisplay(self, self, self.screens, isLive)
self.image_manager = self.parent().image_manager
self.loopList = [
u'Play Slides Menu',
@@ -334,7 +333,7 @@ class SlideController(QtGui.QWidget):
def getControlPanel(self):
return self.controllerLayout
- def sendToPlugins(self, v1=None, v2=None, v3=None, v4=None, v5=None):
+ def sendToPlugins(self, **kwargs):
"""
This is the generic function to send signal for control widgets,
created from within other plugins
@@ -342,7 +341,7 @@ class SlideController(QtGui.QWidget):
"""
sender = self.sender().objectName() or self.sender().text()
controller = self
- Receiver.send_message('%s' % sender, [controller, v1, v2, v3, v4, v5])
+ Receiver.send_message('%s' % sender, [controller, kwargs])
def setPreviewHotkeys(self, parent=None):
self.previousItem.setObjectName(u'previousItemPreview')
diff --git a/openlp/plugins/media/lib/__init__.py b/openlp/plugins/media/lib/__init__.py
index 8b56a6bc9..1855e4c08 100644
--- a/openlp/plugins/media/lib/__init__.py
+++ b/openlp/plugins/media/lib/__init__.py
@@ -25,7 +25,7 @@
# Temple Place, Suite 330, Boston, MA 02111-1307 USA #
###############################################################################
-class MediaAPIs(object):
+class MediaAPI(object):
"""
An enumeration for possible APIs.
"""
@@ -71,8 +71,10 @@ class MediaAPI(object):
Specialiced Media API class
to reflect Features of the related API
"""
- def __init__(self, parent):
+ def __init__(self, parent, name=u'MediaApi'):
self.parent = parent
+ self.name = name
+ self.available = self.check_available()
self.isActive = False
self.canBackground = False
self.state = MediaState.Off
@@ -80,6 +82,13 @@ class MediaAPI(object):
self.audio_extensions_list = []
self.video_extensions_list = []
+ def check_available(self):
+ """
+ API is available on this machine
+ """
+ return False
+
+
def setup(self, display):
"""
Create the related widgets for the current display
@@ -164,6 +173,26 @@ class MediaAPI(object):
"""
pass
+ def display_css(self):
+ """
+ Add css style sheets to htmlbuilder
+ """
+ return u''
+
+
+ def display_javascript(self):
+ """
+ Add javascript functions to htmlbuilder
+ """
+ return u''
+
+
+ def display_html(self):
+ """
+ Add html code to htmlbuilder
+ """
+ return u''
+
from mediaitem import MediaMediaItem
from mediatab import MediaTab
from mediamanager import MediaManager
diff --git a/openlp/plugins/media/lib/mediaitem.py b/openlp/plugins/media/lib/mediaitem.py
index 5aeca1e92..ba6d0b9c6 100644
--- a/openlp/plugins/media/lib/mediaitem.py
+++ b/openlp/plugins/media/lib/mediaitem.py
@@ -92,7 +92,7 @@ class MediaMediaItem(MediaManagerItem):
"""
self.resetAction.setVisible(False)
Receiver.send_message(u'media_reset',
- self.parent.liveController)
+ self.plugin.liveController)
def videobackgroundReplaced(self):
"""
@@ -112,7 +112,7 @@ class MediaMediaItem(MediaManagerItem):
if os.path.exists(filename):
(path, name) = os.path.split(filename)
Receiver.send_message(u'media_video',
- [self.parent.liveController, filename, 0, True])
+ [self.plugin.liveController, filename, 0, True])
self.resetAction.setVisible(True)
else:
critical_error_message_box(UiStrings().LiveBGError,
@@ -139,7 +139,7 @@ class MediaMediaItem(MediaManagerItem):
ItemCapabilities.AllowsVariableStartTime)
service_item.title = unicode(self.plugin.nameStrings[u'singular'])
service_item.add_capability(ItemCapabilities.RequiresMedia)
- #Receiver.send_message(u'media_video', [self.parent.liveController, filename, False])
+ #Receiver.send_message(u'media_video', [self.plugin.liveController, filename, False])
# force a non-existent theme
service_item.theme = -1
frame = u':/media/image_clapperboard.png'
diff --git a/openlp/plugins/media/lib/mediamanager.py b/openlp/plugins/media/lib/mediamanager.py
index 1e9a4c123..3bf4355ae 100644
--- a/openlp/plugins/media/lib/mediamanager.py
+++ b/openlp/plugins/media/lib/mediamanager.py
@@ -63,13 +63,6 @@ class MediaManager(object):
self.APIs = {}
self.controller = []
self.curDisplayMediaAPI = {}
- #Create API Controllers
- if WebkitAPI.is_available():
- self.APIs[u'Webkit'] = WebkitAPI(self)
- if PhononAPI.is_available():
- self.APIs[u'Phonon'] = PhononAPI(self)
- if VlcAPI.is_available():
- self.APIs[u'Vlc'] = VlcAPI(self)
#Timer for video state
self.Timer = QtCore.QTimer()
self.Timer.setInterval(200)
@@ -117,6 +110,33 @@ class MediaManager(object):
if not isAnyonePlaying:
self.Timer.stop()
+ def display_css(self):
+ """
+ Add css style sheets to htmlbuilder
+ """
+ css = u'';
+ for api in self.APIs.values():
+ css+= api.display_css()
+ return css
+
+ def display_javascript(self):
+ """
+ Add javascript functions to htmlbuilder
+ """
+ js = u''
+ for api in self.APIs.values():
+ js+= api.display_javascript()
+ return js
+
+ def display_html(self):
+ """
+ Add html code to htmlbuilder
+ """
+ html = u''
+ for api in self.APIs.values():
+ html+= api.display_html()
+ return html
+
def addControllerItems(self, controller, control_panel):
self.controller.append(controller)
self.setup_generic_controls(controller, control_panel)
@@ -133,11 +153,11 @@ class MediaManager(object):
controller.sendToPlugins)
controller.mediabar.addToolbarButton(
u'Media Pause', u':/slides/media_playback_pause.png',
- translate('OpenLP.SlideController', 'Start playing media'),
+ translate('OpenLP.SlideController', 'Pause playing media'),
controller.sendToPlugins)
controller.mediabar.addToolbarButton(
u'Media Stop', u':/slides/media_playback_stop.png',
- translate('OpenLP.SlideController', 'Start playing media'),
+ translate('OpenLP.SlideController', 'Stop playing media'),
controller.sendToPlugins)
# Build the seekSlider.
controller.seekSlider = QtGui.QSlider(QtCore.Qt.Horizontal)
diff --git a/openlp/plugins/media/lib/mediatab.py b/openlp/plugins/media/lib/mediatab.py
index f0a33130b..97e9c6250 100644
--- a/openlp/plugins/media/lib/mediatab.py
+++ b/openlp/plugins/media/lib/mediatab.py
@@ -33,23 +33,26 @@ class MediaTab(SettingsTab):
"""
MediaTab is the Media settings tab in the settings dialog.
"""
- def __init__(self, parent, title, visible_title, icon_path):
+ def __init__(self, parent, title, visible_title, apis, icon_path):
+ self.apis = apis
SettingsTab.__init__(self, parent, title, visible_title, icon_path)
def setupUi(self):
self.setObjectName(u'MediaTab')
SettingsTab.setupUi(self)
- self.mediaAPIsGroupBox = QtGui.QGroupBox(self.leftColumn)
- self.mediaAPIsGroupBox.setObjectName(u'mediaAPIsGroupBox')
- self.mediaApiLayout = QtGui.QVBoxLayout(self.mediaAPIsGroupBox)
+ self.mediaAPIGroupBox = QtGui.QGroupBox(self.leftColumn)
+ self.mediaAPIGroupBox.setObjectName(u'mediaAPIGroupBox')
+ self.mediaApiLayout = QtGui.QVBoxLayout(self.mediaAPIGroupBox)
self.mediaApiLayout.setObjectName(u'mediaApiLayout')
- self.usePhononCheckBox = QtGui.QCheckBox(self.mediaAPIsGroupBox)
- self.usePhononCheckBox.setObjectName(u'usePhononCheckBox')
- self.mediaApiLayout.addWidget(self.usePhononCheckBox)
- self.useVlcCheckBox = QtGui.QCheckBox(self.mediaAPIsGroupBox)
- self.useVlcCheckBox.setObjectName(u'useVlcCheckBox')
- self.mediaApiLayout.addWidget(self.useVlcCheckBox)
- self.leftLayout.addWidget(self.mediaAPIsGroupBox)
+ self.ApiCheckBoxes = {}
+ for key in self.apis:
+ api = self.apis[key]
+ checkbox = QtGui.QCheckBox(self.mediaAPIGroupBox)
+ checkbox.setEnabled(api.available)
+ checkbox.setObjectName(api.name + u'CheckBox')
+ self.ApiCheckBoxes[api.name] = checkbox
+ self.mediaApiLayout.addWidget(checkbox)
+ self.leftLayout.addWidget(self.mediaAPIGroupBox)
self.apiOrderGroupBox = QtGui.QGroupBox(self.leftColumn)
self.apiOrderGroupBox.setObjectName(u'apiOrderGroupBox')
@@ -87,24 +90,30 @@ class MediaTab(SettingsTab):
self.leftLayout.addWidget(self.apiOrderGroupBox)
self.leftLayout.addStretch()
self.rightLayout.addStretch()
- QtCore.QObject.connect(self.usePhononCheckBox,
- QtCore.SIGNAL(u'stateChanged(int)'),
- self.onUsePhononCheckBoxChanged)
- QtCore.QObject.connect(self.useVlcCheckBox,
- QtCore.SIGNAL(u'stateChanged(int)'),
- self.onUseVlcCheckBoxChanged)
+ for key in self.apis:
+ api = self.apis[key]
+ checkbox = self.ApiCheckBoxes[api.name]
+ QtCore.QObject.connect(checkbox,
+ QtCore.SIGNAL(u'stateChanged(int)'),
+ self.onApiCheckBoxChanged)
+
QtCore.QObject.connect(self.orderingUpButton,
QtCore.SIGNAL(u'pressed()'), self.onOrderingUpButtonPressed)
QtCore.QObject.connect(self.orderingDownButton,
QtCore.SIGNAL(u'pressed()'), self.onOrderingDownButtonPressed)
def retranslateUi(self):
- self.mediaAPIsGroupBox.setTitle(
+ self.mediaAPIGroupBox.setTitle(
translate('MediaPlugin.MediaTab', 'Media APIs'))
- self.usePhononCheckBox.setText(
- translate('MediaPlugin.MediaTab', 'use Phonon'))
- self.useVlcCheckBox.setText(
- translate('MediaPlugin.MediaTab', 'use Vlc'))
+ for key in self.apis:
+ api = self.apis[key]
+ checkbox = self.ApiCheckBoxes[api.name]
+ if api.available:
+ checkbox.setText(api.name)
+ else:
+ checkbox.setText(
+ unicode(translate('MediaPlugin.MediaTab',
+ '%s (unavailable)')) % api.name)
self.apiOrderGroupBox.setTitle(
translate('MediaPlugin.MediaTab', 'API Order'))
self.orderingDownButton.setText(
@@ -112,24 +121,13 @@ class MediaTab(SettingsTab):
self.orderingUpButton.setText(
translate('MediaPlugin.MediaTab', 'Up'))
- def onUsePhononCheckBoxChanged(self, check_state):
+ def onApiCheckBoxChanged(self, check_state):
+ api = self.sender().text()
if check_state == QtCore.Qt.Checked:
- self.usePhonon = True
- if u'Phonon' not in self.usedAPIs:
- self.usedAPIs.append(u'Phonon')
+ if api not in self.usedAPIs:
+ self.usedAPIs.append(api)
else:
- self.usePhonon = False
- self.usedAPIs.takeAt(self.usedAPIs.indexOf(u'Phonon'))
- self.updateApiList()
-
- def onUseVlcCheckBoxChanged(self, check_state):
- if check_state == QtCore.Qt.Checked:
- self.useVlc = True
- if u'Vlc' not in self.usedAPIs:
- self.usedAPIs.append(u'Vlc')
- else:
- self.useVlc = False
- self.usedAPIs.takeAt(self.usedAPIs.indexOf(u'Vlc'))
+ self.usedAPIs.takeAt(self.usedAPIs.indexOf(api))
self.updateApiList()
def updateApiList(self):
@@ -157,11 +155,11 @@ class MediaTab(SettingsTab):
self.usedAPIs = QtCore.QSettings().value(
self.settingsSection + u'/apis',
QtCore.QVariant(u'Webkit')).toString().split(u',')
- self.useWebkit = u'Webkit' in self.usedAPIs
- self.usePhonon = u'Phonon' in self.usedAPIs
- self.useVlc = u'Vlc' in self.usedAPIs
- self.usePhononCheckBox.setChecked(self.usePhonon)
- self.useVlcCheckBox.setChecked(self.useVlc)
+ for key in self.apis:
+ api = self.apis[key]
+ checkbox = self.ApiCheckBoxes[api.name]
+ if api.available and api.name in self.usedAPIs:
+ checkbox.setChecked(True)
self.updateApiList()
def save(self):
diff --git a/openlp/plugins/media/lib/phononapi.py b/openlp/plugins/media/lib/phononapi.py
index 8f1fc8c8c..cc8c70ea3 100644
--- a/openlp/plugins/media/lib/phononapi.py
+++ b/openlp/plugins/media/lib/phononapi.py
@@ -44,7 +44,7 @@ class PhononAPI(MediaAPI):
"""
def __init__(self, parent):
- MediaAPI.__init__(self, parent)
+ MediaAPI.__init__(self, parent, u'Phonon')
self.parent = parent
self.additional_extensions = {
u'audio/ac3': [u'.ac3'],
@@ -76,7 +76,7 @@ class PhononAPI(MediaAPI):
ext = u'*%s' % extension
if ext not in list:
list.append(ext)
- self.parent.parent.serviceManager.supportedSuffixes(extension[1:])
+ self.parent.serviceManager.supportedSuffixes(extension[1:])
log.info(u'MediaPlugin: %s extensions: %s' % (mimetype,
u' '.join(extensions)))
# Add extensions for this mimetype from self.additional_extensions.
@@ -87,7 +87,7 @@ class PhononAPI(MediaAPI):
ext = u'*%s' % extension
if ext not in list:
list.append(ext)
- self.parent.parent.serviceManager.supportedSuffixes(extension[1:])
+ self.parent.serviceManager.supportedSuffixes(extension[1:])
log.info(u'MediaPlugin: %s additional extensions: %s' % (mimetype,
u' '.join(self.additional_extensions[mimetype])))
@@ -107,10 +107,7 @@ class PhononAPI(MediaAPI):
display.phononWidget.hide()
self.hasOwnWidget = True
- @staticmethod
- def is_available():
-# usePhonon = QtCore.QSettings().value(
-# u'media/use phonon', QtCore.QVariant(True)).toBool()
+ def check_available(self):
return True
def get_supported_file_types(self):
diff --git a/openlp/plugins/media/lib/vlcapi.py b/openlp/plugins/media/lib/vlcapi.py
index 7531ba394..94cd067fa 100644
--- a/openlp/plugins/media/lib/vlcapi.py
+++ b/openlp/plugins/media/lib/vlcapi.py
@@ -30,8 +30,10 @@ import sys, os
from datetime import datetime
try:
import vlc
-except:
- pass
+ vlc_available = True
+except ImportError:
+ vlc_available = False
+
from PyQt4 import QtCore, QtGui
from openlp.core.lib import Receiver
from openlp.plugins.media.lib import MediaAPI, MediaState
@@ -44,7 +46,7 @@ class VlcAPI(MediaAPI):
to reflect Features of the Vlc API
"""
def __init__(self, parent):
- MediaAPI.__init__(self, parent)
+ MediaAPI.__init__(self, parent, u'Vlc')
self.parent = parent
self.video_extensions_list = [
u'*.3gp'
@@ -99,13 +101,8 @@ class VlcAPI(MediaAPI):
display.vlcMediaPlayer.set_agl(int(display.vlcWidget.winId()))
self.hasOwnWidget = True
- @staticmethod
- def is_available():
- try:
- import vlc
- return True
- except:
- return False
+ def check_available(self):
+ return vlc_available
def get_supported_file_types(self):
self.supported_file_types = ['avi']
diff --git a/openlp/plugins/media/lib/webkitapi.py b/openlp/plugins/media/lib/webkitapi.py
index 7c2108ea7..ca8d4d1a1 100644
--- a/openlp/plugins/media/lib/webkitapi.py
+++ b/openlp/plugins/media/lib/webkitapi.py
@@ -41,7 +41,7 @@ class WebkitAPI(MediaAPI):
"""
def __init__(self, parent):
- MediaAPI.__init__(self, parent)
+ MediaAPI.__init__(self, parent, u'Webkit')
self.parent = parent
self.canBackground = True
self.video_extensions_list = [
@@ -73,12 +73,194 @@ class WebkitAPI(MediaAPI):
# no special controls
pass
+ def display_css(self):
+ """
+ Add css style sheets to htmlbuilder
+ """
+ css = u'''
+ '''
+ return css
+
+
+ def display_javascript(self):
+ """
+ Add javascript functions to htmlbuilder
+ """
+ js = u'''
+ var video_timer = null;
+ var current_video = '1';
+
+ function show_video(state, path, volume, loop, seekVal){
+ // Note, the preferred method for looping would be to use the
+ // video tag loop attribute.
+ // But QtWebKit doesn't support this. Neither does it support the
+ // onended event, hence the setInterval()
+ // In addition, setting the currentTime attribute to zero to restart
+ // the video raises an INDEX_SIZE_ERROR: DOM Exception 1
+ // To complicate it further, sometimes vid.currentTime stops
+ // slightly short of vid.duration and vid.ended is intermittent!
+ //
+ // Note, currently the background may go black between loops. Not
+ // desirable. Need to investigate using two