openlp/openlp/core/ui/slidecontroller.py

1114 lines
47 KiB
Python
Raw Normal View History

# -*- coding: utf-8 -*-
# vim: autoindent shiftwidth=4 expandtab textwidth=80 tabstop=4 softtabstop=4
###############################################################################
# OpenLP - Open Source Lyrics Projection #
# --------------------------------------------------------------------------- #
2010-12-26 11:04:47 +00:00
# Copyright (c) 2008-2011 Raoul Snyman #
# Portions copyright (c) 2008-2011 Tim Bentley, Jonathan Corwin, Michael #
# Gorven, Scott Guerrieri, Meinert Jordan, Armin Köhler, Andreas Preikschat, #
# Christian Richter, Philip Ridout, Maikel Stuivenberg, Martin Thompson, Jon #
# Tibble, Carsten Tinggaard, Frode Woldsund #
# --------------------------------------------------------------------------- #
# 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 #
###############################################################################
2009-05-02 11:16:08 +00:00
import logging
2009-11-09 20:27:25 +00:00
import os
2009-05-02 11:16:08 +00:00
from PyQt4 import QtCore, QtGui
from PyQt4.phonon import Phonon
2010-04-29 20:56:27 +00:00
from openlp.core.lib import OpenLPToolbar, Receiver, resize_image, \
ItemCapabilities, translate
from openlp.core.lib.ui import icon_action, UiStrings, shortcut_action
2011-02-04 02:56:59 +00:00
from openlp.core.ui import HideMode, MainDisplay
2009-10-20 16:33:00 +00:00
2010-02-27 15:31:23 +00:00
log = logging.getLogger(__name__)
class SlideList(QtGui.QTableWidget):
2009-08-09 12:05:54 +00:00
"""
Customised version of QTableWidget which can respond to keyboard
events.
"""
def __init__(self, parent=None, name=None):
2011-01-21 20:56:09 +00:00
QtGui.QTableWidget.__init__(self, parent.controller)
self.parent = parent
2010-12-26 14:44:07 +00:00
class SlideController(QtGui.QWidget):
"""
2009-09-21 17:56:36 +00:00
SlideController is the slide controller widget. This widget is what the
user uses to control the displaying of verses/slides/etc on the screen.
"""
2010-07-17 08:59:15 +00:00
def __init__(self, parent, settingsmanager, screens, isLive=False):
"""
Set up the Slide Controller.
"""
QtGui.QWidget.__init__(self, parent)
2009-09-06 19:23:57 +00:00
self.settingsmanager = settingsmanager
self.isLive = isLive
self.parent = parent
2010-07-17 08:59:15 +00:00
self.screens = screens
2010-07-24 16:55:06 +00:00
self.ratio = float(self.screens.current[u'size'].width()) / \
float(self.screens.current[u'size'].height())
2010-07-23 05:05:34 +00:00
self.display = MainDisplay(self, screens, isLive)
2010-05-10 18:19:45 +00:00
self.loopList = [
2009-10-24 16:00:43 +00:00
u'Start Loop',
2009-10-24 13:07:41 +00:00
u'Loop Separator',
2009-10-24 16:00:43 +00:00
u'Image SpinBox'
]
2010-05-10 18:19:45 +00:00
self.songEditList = [
2009-10-24 16:00:43 +00:00
u'Edit Song',
2009-10-24 13:07:41 +00:00
]
2010-08-02 05:16:07 +00:00
self.volume = 10
self.timer_id = 0
2009-10-24 18:11:02 +00:00
self.songEdit = False
self.selectedRow = 0
self.serviceItem = None
2010-08-01 08:28:31 +00:00
self.alertTab = None
2011-02-07 22:07:48 +00:00
self.panel = QtGui.QWidget(parent.controlSplitter)
self.slideList = {}
# Layout for holding panel
2011-02-01 18:05:59 +00:00
self.panelLayout = QtGui.QVBoxLayout(self.panel)
2011-01-21 20:53:08 +00:00
self.panelLayout.setSpacing(0)
self.panelLayout.setMargin(0)
# Type label for the top of the slide controller
2011-02-01 18:05:59 +00:00
self.typeLabel = QtGui.QLabel(self.panel)
if self.isLive:
2011-02-09 05:04:12 +00:00
self.typeLabel.setText(UiStrings.Live)
2009-11-08 17:02:46 +00:00
self.split = 1
2010-05-10 18:19:45 +00:00
self.typePrefix = u'live'
else:
2011-02-09 05:04:12 +00:00
self.typeLabel.setText(UiStrings.Preview)
2009-11-08 17:02:46 +00:00
self.split = 0
2010-05-10 18:19:45 +00:00
self.typePrefix = u'preview'
2011-01-21 20:56:09 +00:00
self.typeLabel.setStyleSheet(u'font-weight: bold; font-size: 12pt;')
self.typeLabel.setAlignment(QtCore.Qt.AlignCenter)
self.panelLayout.addWidget(self.typeLabel)
# Splitter
2011-02-01 18:05:59 +00:00
self.splitter = QtGui.QSplitter(self.panel)
2011-01-21 20:56:09 +00:00
self.splitter.setOrientation(QtCore.Qt.Vertical)
self.panelLayout.addWidget(self.splitter)
# Actual controller section
2011-01-21 20:56:09 +00:00
self.controller = QtGui.QWidget(self.splitter)
2011-01-21 20:53:08 +00:00
self.controller.setGeometry(QtCore.QRect(0, 0, 100, 536))
self.controller.setSizePolicy(
QtGui.QSizePolicy(QtGui.QSizePolicy.Preferred,
QtGui.QSizePolicy.Maximum))
2011-01-21 20:53:08 +00:00
self.controllerLayout = QtGui.QVBoxLayout(self.controller)
self.controllerLayout.setSpacing(0)
self.controllerLayout.setMargin(0)
# Controller list view
2011-01-21 20:53:08 +00:00
self.previewListWidget = SlideList(self)
self.previewListWidget.setColumnCount(1)
self.previewListWidget.horizontalHeader().setVisible(False)
2011-03-04 15:31:34 +00:00
self.previewListWidget.setColumnWidth(0, self.controller.width())
2011-01-21 20:53:08 +00:00
self.previewListWidget.isLive = self.isLive
self.previewListWidget.setObjectName(u'PreviewListWidget')
self.previewListWidget.setSelectionBehavior(1)
self.previewListWidget.setSelectionMode(
QtGui.QAbstractItemView.SingleSelection)
2011-01-21 20:53:08 +00:00
self.previewListWidget.setEditTriggers(
2009-11-04 01:16:15 +00:00
QtGui.QAbstractItemView.NoEditTriggers)
2011-01-21 20:53:08 +00:00
self.previewListWidget.setHorizontalScrollBarPolicy(
2010-04-27 22:36:50 +00:00
QtCore.Qt.ScrollBarAlwaysOff)
2011-01-21 20:53:08 +00:00
self.previewListWidget.setAlternatingRowColors(True)
self.controllerLayout.addWidget(self.previewListWidget)
# Build the full toolbar
2011-01-21 20:56:09 +00:00
self.toolbar = OpenLPToolbar(self)
sizeToolbarPolicy = QtGui.QSizePolicy(QtGui.QSizePolicy.Fixed,
QtGui.QSizePolicy.Fixed)
sizeToolbarPolicy.setHorizontalStretch(0)
sizeToolbarPolicy.setVerticalStretch(0)
sizeToolbarPolicy.setHeightForWidth(
2011-01-21 20:56:09 +00:00
self.toolbar.sizePolicy().hasHeightForWidth())
self.toolbar.setSizePolicy(sizeToolbarPolicy)
self.previousItem = self.toolbar.addToolbarButton(
2011-01-19 21:17:32 +00:00
translate('OpenLP.SlideController', 'Previous Slide'),
u':/slides/slide_previous.png',
2010-07-22 06:02:31 +00:00
translate('OpenLP.SlideController', 'Move to previous'),
self.onSlideSelectedPrevious)
2011-01-21 20:56:09 +00:00
self.nextItem = self.toolbar.addToolbarButton(
2011-01-19 21:17:32 +00:00
translate('OpenLP.SlideController', 'Next Slide'),
u':/slides/slide_next.png',
2010-07-22 06:02:31 +00:00
translate('OpenLP.SlideController', 'Move to next'),
self.onSlideSelectedNext)
self.toolbar.addToolbarSeparator(u'Close Separator')
if self.isLive:
2011-01-22 08:59:46 +00:00
self.hideMenu = QtGui.QToolButton(self.toolbar)
self.hideMenu.setText(translate('OpenLP.SlideController', 'Hide'))
self.hideMenu.setPopupMode(QtGui.QToolButton.MenuButtonPopup)
self.toolbar.addToolbarWidget(u'Hide Menu', self.hideMenu)
self.hideMenu.setMenu(QtGui.QMenu(
2011-01-21 20:56:09 +00:00
translate('OpenLP.SlideController', 'Hide'), self.toolbar))
self.blankScreen = icon_action(self.hideMenu, u'Blank Screen',
u':/slides/slide_blank.png', False)
self.blankScreen.setText(
translate('OpenLP.SlideController', 'Blank Screen'))
self.themeScreen = icon_action(self.hideMenu, u'Blank Theme',
u':/slides/slide_theme.png', False)
self.themeScreen.setText(
translate('OpenLP.SlideController', 'Blank to Theme'))
self.desktopScreen = icon_action(self.hideMenu, u'Desktop Screen',
u':/slides/slide_desktop.png', False)
self.desktopScreen.setText(
translate('OpenLP.SlideController', 'Show Desktop'))
2011-03-04 15:31:34 +00:00
self.desktopScreen.setVisible(self.screens.display_count > 1)
2011-01-22 08:59:46 +00:00
self.hideMenu.setDefaultAction(self.blankScreen)
self.hideMenu.menu().addAction(self.blankScreen)
self.hideMenu.menu().addAction(self.themeScreen)
self.hideMenu.menu().addAction(self.desktopScreen)
2011-01-21 20:56:09 +00:00
self.toolbar.addToolbarSeparator(u'Loop Separator')
self.toolbar.addToolbarButton(
2011-02-09 17:30:38 +00:00
# Does not need translating - control string.
2010-04-30 21:00:17 +00:00
u'Start Loop', u':/media/media_time.png',
2010-07-22 06:02:31 +00:00
translate('OpenLP.SlideController', 'Start continuous loop'),
self.onStartLoop)
2011-01-21 20:56:09 +00:00
self.toolbar.addToolbarButton(
2011-02-09 17:30:38 +00:00
# Does not need translating - control string.
2009-10-24 16:00:43 +00:00
u'Stop Loop', u':/media/media_stop.png',
2010-07-22 06:02:31 +00:00
translate('OpenLP.SlideController', 'Stop continuous loop'),
self.onStopLoop)
2011-02-01 18:05:59 +00:00
self.delaySpinBox = QtGui.QSpinBox()
self.delaySpinBox.setMinimum(1)
self.delaySpinBox.setMaximum(180)
self.toolbar.addToolbarWidget(u'Image SpinBox', self.delaySpinBox)
2011-02-13 15:11:06 +00:00
self.delaySpinBox.setSuffix(UiStrings.S)
2011-02-01 18:05:59 +00:00
self.delaySpinBox.setToolTip(translate('OpenLP.SlideController',
2010-07-13 16:00:33 +00:00
'Delay between slides in seconds'))
2010-12-27 10:14:46 +00:00
else:
2011-01-21 20:56:09 +00:00
self.toolbar.addToolbarButton(
2011-02-09 17:30:38 +00:00
# Does not need translating - control string.
2010-12-27 10:14:46 +00:00
u'Go Live', u':/general/general_live.png',
translate('OpenLP.SlideController', 'Move to live'),
self.onGoLive)
2011-01-21 20:56:09 +00:00
self.toolbar.addToolbarSeparator(u'Close Separator')
self.toolbar.addToolbarButton(
2011-02-09 17:30:38 +00:00
# Does not need translating - control string.
2010-12-27 10:14:46 +00:00
u'Edit Song', u':/general/general_edit.png',
translate('OpenLP.SlideController',
'Edit and reload song preview'),
self.onEditSong)
2011-01-21 20:56:09 +00:00
self.controllerLayout.addWidget(self.toolbar)
2010-07-25 09:03:01 +00:00
# Build a Media ToolBar
2011-01-22 08:59:46 +00:00
self.mediabar = OpenLPToolbar(self)
self.mediabar.addToolbarButton(
2010-04-30 21:00:17 +00:00
u'Media Start', u':/slides/media_playback_start.png',
2010-07-22 06:02:31 +00:00
translate('OpenLP.SlideController', 'Start playing media'),
self.onMediaPlay)
2011-01-22 08:59:46 +00:00
self.mediabar.addToolbarButton(
2010-04-30 21:00:17 +00:00
u'Media Pause', u':/slides/media_playback_pause.png',
2010-07-22 06:02:31 +00:00
translate('OpenLP.SlideController', 'Start playing media'),
self.onMediaPause)
2011-01-22 08:59:46 +00:00
self.mediabar.addToolbarButton(
2010-04-30 21:00:17 +00:00
u'Media Stop', u':/slides/media_playback_stop.png',
2010-07-22 06:02:31 +00:00
translate('OpenLP.SlideController', 'Start playing media'),
self.onMediaStop)
2010-12-26 14:44:07 +00:00
if self.isLive:
2010-12-27 10:14:46 +00:00
# Build the Song Toolbar
2011-01-22 08:59:46 +00:00
self.songMenu = QtGui.QToolButton(self.toolbar)
2011-03-04 15:31:34 +00:00
self.songMenu.setText(translate('OpenLP.SlideController', 'Go To'))
2011-01-22 08:59:46 +00:00
self.songMenu.setPopupMode(QtGui.QToolButton.InstantPopup)
self.toolbar.addToolbarWidget(u'Song Menu', self.songMenu)
self.songMenu.setMenu(QtGui.QMenu(
2011-01-21 20:56:09 +00:00
translate('OpenLP.SlideController', 'Go To'), self.toolbar))
self.toolbar.makeWidgetsInvisible([u'Song Menu'])
2010-12-27 10:14:46 +00:00
# Build the volumeSlider.
self.volumeSlider = QtGui.QSlider(QtCore.Qt.Horizontal)
self.volumeSlider.setTickInterval(1)
self.volumeSlider.setTickPosition(QtGui.QSlider.TicksAbove)
self.volumeSlider.setMinimum(0)
self.volumeSlider.setMaximum(10)
else:
# Build the seekSlider.
self.seekSlider = Phonon.SeekSlider()
self.seekSlider.setGeometry(QtCore.QRect(90, 260, 221, 24))
self.seekSlider.setObjectName(u'seekSlider')
2011-01-22 08:59:46 +00:00
self.mediabar.addToolbarWidget(u'Seek Slider', self.seekSlider)
2010-12-27 10:14:46 +00:00
self.volumeSlider = Phonon.VolumeSlider()
self.volumeSlider.setGeometry(QtCore.QRect(90, 260, 221, 24))
self.volumeSlider.setObjectName(u'volumeSlider')
2011-01-22 08:59:46 +00:00
self.mediabar.addToolbarWidget(u'Audio Volume', self.volumeSlider)
self.controllerLayout.addWidget(self.mediabar)
# Screen preview area
2011-01-22 08:59:46 +00:00
self.previewFrame = QtGui.QFrame(self.splitter)
self.previewFrame.setGeometry(QtCore.QRect(0, 0, 300, 300 * self.ratio))
self.previewFrame.setMinimumHeight(100)
self.previewFrame.setSizePolicy(QtGui.QSizePolicy(
2010-12-26 14:44:07 +00:00
QtGui.QSizePolicy.Ignored, QtGui.QSizePolicy.Ignored,
2010-04-16 07:31:01 +00:00
QtGui.QSizePolicy.Label))
2011-01-22 08:59:46 +00:00
self.previewFrame.setFrameShape(QtGui.QFrame.StyledPanel)
self.previewFrame.setFrameShadow(QtGui.QFrame.Sunken)
self.previewFrame.setObjectName(u'PreviewFrame')
self.grid = QtGui.QGridLayout(self.previewFrame)
self.grid.setMargin(8)
self.grid.setObjectName(u'grid')
2011-01-22 08:59:46 +00:00
self.slideLayout = QtGui.QVBoxLayout()
self.slideLayout.setSpacing(0)
self.slideLayout.setMargin(0)
self.slideLayout.setObjectName(u'SlideLayout')
2009-11-09 20:27:25 +00:00
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)
if not self.isLive:
self.video.setGeometry(QtCore.QRect(0, 0, 300, 225))
2011-01-22 08:59:46 +00:00
self.slideLayout.insertWidget(0, self.video)
# Actual preview screen
2011-01-22 08:59:46 +00:00
self.slidePreview = QtGui.QLabel(self)
2009-08-23 20:15:05 +00:00
sizePolicy = QtGui.QSizePolicy(QtGui.QSizePolicy.Fixed,
QtGui.QSizePolicy.Fixed)
sizePolicy.setHorizontalStretch(0)
sizePolicy.setVerticalStretch(0)
sizePolicy.setHeightForWidth(
2011-01-22 08:59:46 +00:00
self.slidePreview.sizePolicy().hasHeightForWidth())
self.slidePreview.setSizePolicy(sizePolicy)
self.slidePreview.setFixedSize(
QtCore.QSize(self.settingsmanager.slidecontroller_image,
2010-08-28 15:49:51 +00:00
self.settingsmanager.slidecontroller_image / self.ratio))
2011-01-22 08:59:46 +00:00
self.slidePreview.setFrameShape(QtGui.QFrame.Box)
self.slidePreview.setFrameShadow(QtGui.QFrame.Plain)
self.slidePreview.setLineWidth(1)
self.slidePreview.setScaledContents(True)
self.slidePreview.setObjectName(u'SlidePreview')
self.slideLayout.insertWidget(0, self.slidePreview)
self.grid.addLayout(self.slideLayout, 0, 0, 1, 1)
# Signals
2011-01-21 20:53:08 +00:00
QtCore.QObject.connect(self.previewListWidget,
2009-08-23 20:15:05 +00:00
QtCore.SIGNAL(u'clicked(QModelIndex)'), self.onSlideSelected)
2010-12-26 14:44:07 +00:00
if self.isLive:
2011-01-22 08:59:46 +00:00
QtCore.QObject.connect(self.blankScreen,
2010-12-27 10:14:46 +00:00
QtCore.SIGNAL(u'triggered(bool)'), self.onBlankDisplay)
2011-01-22 08:59:46 +00:00
QtCore.QObject.connect(self.themeScreen,
2010-12-27 10:14:46 +00:00
QtCore.SIGNAL(u'triggered(bool)'), self.onThemeDisplay)
2011-03-04 15:31:34 +00:00
QtCore.QObject.connect(self.desktopScreen,
QtCore.SIGNAL(u'triggered(bool)'), self.onHideDisplay)
2010-12-27 10:14:46 +00:00
QtCore.QObject.connect(self.volumeSlider,
QtCore.SIGNAL(u'sliderReleased()'), self.mediaVolume)
QtCore.QObject.connect(Receiver.get_receiver(),
QtCore.SIGNAL(u'maindisplay_active'), self.updatePreview)
2009-08-29 07:17:56 +00:00
QtCore.QObject.connect(Receiver.get_receiver(),
2010-04-16 07:31:01 +00:00
QtCore.SIGNAL(u'slidecontroller_live_spin_delay'),
2010-12-21 19:39:35 +00:00
self.receiveSpinDelay)
2011-01-21 20:56:09 +00:00
self.toolbar.makeWidgetsInvisible(self.loopList)
self.toolbar.actions[u'Stop Loop'].setVisible(False)
2009-10-24 13:07:41 +00:00
else:
2011-01-21 20:53:08 +00:00
QtCore.QObject.connect(self.previewListWidget,
2010-12-27 10:14:46 +00:00
QtCore.SIGNAL(u'doubleClicked(QModelIndex)'),
self.onGoLiveClick)
2011-01-21 20:56:09 +00:00
self.toolbar.makeWidgetsInvisible(self.songEditList)
2011-01-22 08:59:46 +00:00
self.mediabar.setVisible(False)
if self.isLive:
self.setLiveHotkeys(self)
2011-02-04 03:31:06 +00:00
self.__addActionsToWidget(self.previewListWidget)
self.__addActionsToWidget(self.display)
else:
2010-12-08 21:03:25 +00:00
self.setPreviewHotkeys()
2011-01-21 20:53:08 +00:00
self.previewListWidget.addActions(
2011-01-19 21:17:32 +00:00
[self.nextItem,
self.previousItem])
2010-03-02 19:44:55 +00:00
QtCore.QObject.connect(Receiver.get_receiver(),
2010-05-10 18:19:45 +00:00
QtCore.SIGNAL(u'slidecontroller_%s_stop_loop' % self.typePrefix),
2010-04-22 21:22:09 +00:00
self.onStopLoop)
2009-10-17 16:11:41 +00:00
QtCore.QObject.connect(Receiver.get_receiver(),
2010-05-10 18:19:45 +00:00
QtCore.SIGNAL(u'slidecontroller_%s_first' % self.typePrefix),
2010-04-16 07:31:01 +00:00
self.onSlideSelectedFirst)
2009-10-17 16:11:41 +00:00
QtCore.QObject.connect(Receiver.get_receiver(),
2010-05-10 18:19:45 +00:00
QtCore.SIGNAL(u'slidecontroller_%s_next' % self.typePrefix),
2010-04-16 07:31:01 +00:00
self.onSlideSelectedNext)
2009-10-17 16:11:41 +00:00
QtCore.QObject.connect(Receiver.get_receiver(),
2010-05-10 18:19:45 +00:00
QtCore.SIGNAL(u'slidecontroller_%s_previous' % self.typePrefix),
2010-04-16 07:31:01 +00:00
self.onSlideSelectedPrevious)
QtCore.QObject.connect(Receiver.get_receiver(),
2010-05-10 18:19:45 +00:00
QtCore.SIGNAL(u'slidecontroller_%s_next_noloop' % self.typePrefix),
2010-04-16 07:31:01 +00:00
self.onSlideSelectedNextNoloop)
QtCore.QObject.connect(Receiver.get_receiver(),
QtCore.SIGNAL(u'slidecontroller_%s_previous_noloop' %
2010-05-10 18:19:45 +00:00
self.typePrefix),
self.onSlideSelectedPreviousNoloop)
2009-10-17 16:11:41 +00:00
QtCore.QObject.connect(Receiver.get_receiver(),
2010-05-10 18:19:45 +00:00
QtCore.SIGNAL(u'slidecontroller_%s_last' % self.typePrefix),
2010-04-16 07:31:01 +00:00
self.onSlideSelectedLast)
QtCore.QObject.connect(Receiver.get_receiver(),
2010-05-10 18:19:45 +00:00
QtCore.SIGNAL(u'slidecontroller_%s_change' % self.typePrefix),
2010-04-16 07:31:01 +00:00
self.onSlideChange)
QtCore.QObject.connect(Receiver.get_receiver(),
2010-05-10 18:19:45 +00:00
QtCore.SIGNAL(u'slidecontroller_%s_set' % self.typePrefix),
self.onSlideSelectedIndex)
QtCore.QObject.connect(Receiver.get_receiver(),
2010-05-10 18:19:45 +00:00
QtCore.SIGNAL(u'slidecontroller_%s_blank' % self.typePrefix),
self.onSlideBlank)
QtCore.QObject.connect(Receiver.get_receiver(),
2010-05-10 18:19:45 +00:00
QtCore.SIGNAL(u'slidecontroller_%s_unblank' % self.typePrefix),
self.onSlideUnblank)
QtCore.QObject.connect(Receiver.get_receiver(),
2010-05-10 18:19:45 +00:00
QtCore.SIGNAL(u'slidecontroller_%s_text_request' % self.typePrefix),
self.onTextRequest)
2010-07-24 16:55:06 +00:00
QtCore.QObject.connect(Receiver.get_receiver(),
QtCore.SIGNAL(u'config_screen_changed'), self.screenSizeChanged)
2009-11-08 17:02:46 +00:00
def setPreviewHotkeys(self, parent=None):
2011-01-19 21:17:32 +00:00
actionList = self.parent.actionList
self.previousItem.setShortcuts([QtCore.Qt.Key_Up, 0])
actionList.add_action(self.previousItem, u'Preview')
self.nextItem.setShortcuts([QtCore.Qt.Key_Down, 0])
actionList.add_action(self.nextItem, u'Preview')
def setLiveHotkeys(self, parent=None):
2011-01-19 21:17:32 +00:00
actionList = self.parent.actionList
self.previousItem.setShortcuts([QtCore.Qt.Key_Up, QtCore.Qt.Key_PageUp])
self.previousItem.setShortcutContext(
QtCore.Qt.WidgetWithChildrenShortcut)
2011-02-14 21:06:48 +00:00
actionList.add_action(self.previousItem, u'Live')
2011-01-19 21:17:32 +00:00
self.nextItem.setShortcuts([QtCore.Qt.Key_Down, QtCore.Qt.Key_PageDown])
self.nextItem.setShortcutContext(QtCore.Qt.WidgetWithChildrenShortcut)
actionList.add_action(self.nextItem, u'Live')
2011-02-04 02:56:59 +00:00
self.previousService = shortcut_action(parent,
translate('OpenLP.SlideController', 'Previous Service'),
[QtCore.Qt.Key_Left, 0], self.servicePrevious)
2011-01-19 21:17:32 +00:00
actionList.add_action(self.previousService, u'Live')
2011-02-04 02:56:59 +00:00
self.nextService = shortcut_action(parent,
translate('OpenLP.SlideController', 'Next Service'),
[QtCore.Qt.Key_Right, 0], self.serviceNext)
2011-01-19 21:17:32 +00:00
actionList.add_action(self.nextService, u'Live')
2011-02-04 02:56:59 +00:00
self.escapeItem = shortcut_action(parent,
translate('OpenLP.SlideController', 'Escape Item'),
[QtCore.Qt.Key_Escape, 0], self.liveEscape)
2011-01-19 21:17:32 +00:00
actionList.add_action(self.escapeItem, u'Live')
2011-01-15 22:50:25 +00:00
def liveEscape(self):
self.display.setVisible(False)
self.display.videoStop()
2011-01-19 21:17:32 +00:00
def servicePrevious(self):
Receiver.send_message('servicemanager_previous_item')
def serviceNext(self):
Receiver.send_message('servicemanager_next_item')
2010-07-24 16:55:06 +00:00
def screenSizeChanged(self):
"""
Settings dialog has changed the screen size of adjust output and
screen previews.
"""
2011-03-04 15:31:34 +00:00
if self.isLive:
self.desktopScreen.setVisible(self.screens.display_count > 1)
2010-07-24 16:55:06 +00:00
# rebuild display as screen size changed
self.display = MainDisplay(self, self.screens, self.isLive)
2010-12-03 18:56:12 +00:00
self.display.imageManager = self.parent.renderManager.image_manager
2011-02-12 16:07:11 +00:00
self.display.alertTab = self.alertTab
2010-07-24 16:55:06 +00:00
self.display.setup()
if self.isLive:
2011-02-04 03:31:06 +00:00
self.__addActionsToWidget(self.display)
# The SlidePreview's ratio.
self.ratio = float(self.screens.current[u'size'].width()) / \
float(self.screens.current[u'size'].height())
2010-12-26 14:44:07 +00:00
self.previewSizeChanged()
if self.serviceItem:
self.refreshServiceItem()
2010-07-24 16:55:06 +00:00
2011-02-04 03:31:06 +00:00
def __addActionsToWidget(self, widget):
widget.addActions([
self.previousItem, self.nextItem,
self.previousService, self.nextService,
self.escapeItem])
2010-12-26 14:44:07 +00:00
def previewSizeChanged(self):
2009-11-08 17:40:43 +00:00
"""
2010-12-26 14:44:07 +00:00
Takes care of the SlidePreview's size. Is called when one of the the
splitters is moved or when the screen size is changed. Note, that this
method is (also) called frequently from the mainwindow *paintEvent*.
2009-11-08 17:40:43 +00:00
"""
2011-01-22 08:59:46 +00:00
if self.ratio < float(self.previewFrame.width()) / float(
self.previewFrame.height()):
2010-12-26 14:44:07 +00:00
# We have to take the height as limit.
2011-01-22 08:59:46 +00:00
max_height = self.previewFrame.height() - self.grid.margin() * 2
self.slidePreview.setFixedSize(QtCore.QSize(max_height * self.ratio,
2010-12-26 14:44:07 +00:00
max_height))
else:
# We have to take the width as limit.
2011-01-22 08:59:46 +00:00
max_width = self.previewFrame.width() - self.grid.margin() * 2
self.slidePreview.setFixedSize(QtCore.QSize(max_width,
2010-12-26 14:44:07 +00:00
max_width / self.ratio))
2011-01-12 19:31:46 +00:00
# Make sure that the frames have the correct size.
2011-01-21 20:53:08 +00:00
self.previewListWidget.setColumnWidth(0,
self.previewListWidget.viewport().size().width())
2011-01-12 19:31:46 +00:00
if self.serviceItem:
# Sort out songs, bibles, etc.
if self.serviceItem.is_text():
2011-01-21 20:53:08 +00:00
self.previewListWidget.resizeRowsToContents()
else:
# Sort out image heights.
2011-02-07 22:07:48 +00:00
width = self.parent.controlSplitter.sizes()[self.split]
2011-01-12 19:31:46 +00:00
for framenumber in range(len(self.serviceItem.get_frames())):
2011-01-21 20:53:08 +00:00
self.previewListWidget.setRowHeight(
2011-01-12 19:31:46 +00:00
framenumber, width / self.ratio)
2009-08-24 05:10:04 +00:00
2009-10-26 06:09:33 +00:00
def onSongBarHandler(self):
request = unicode(self.sender().text())
2009-12-06 16:50:13 +00:00
slideno = self.slideList[request]
2011-02-01 00:33:50 +00:00
self.__updatePreviewSelection(slideno)
2009-12-02 11:22:48 +00:00
self.onSlideSelected()
2009-10-26 06:09:33 +00:00
2009-08-29 07:17:56 +00:00
def receiveSpinDelay(self, value):
2011-02-01 18:05:59 +00:00
self.delaySpinBox.setValue(int(value))
2009-08-29 07:17:56 +00:00
def enableToolBar(self, item):
2009-08-28 18:27:32 +00:00
"""
Allows the toolbars to be reconfigured based on Controller Type
and ServiceItem Type
"""
if self.isLive:
self.enableLiveToolBar(item)
else:
self.enablePreviewToolBar(item)
def enableLiveToolBar(self, item):
"""
Allows the live toolbar to be customised
"""
2011-01-21 20:56:09 +00:00
self.toolbar.setVisible(True)
2011-01-22 08:59:46 +00:00
self.mediabar.setVisible(False)
2011-01-21 20:56:09 +00:00
self.toolbar.makeWidgetsInvisible([u'Song Menu'])
self.toolbar.makeWidgetsInvisible(self.loopList)
self.toolbar.actions[u'Stop Loop'].setVisible(False)
if item.is_text():
2010-04-28 14:17:42 +00:00
if QtCore.QSettings().value(
2010-12-21 11:09:00 +00:00
self.parent.songsSettingsSection + u'/display songbar',
2010-04-28 14:17:42 +00:00
QtCore.QVariant(True)).toBool() and len(self.slideList) > 0:
2011-01-21 20:56:09 +00:00
self.toolbar.makeWidgetsVisible([u'Song Menu'])
2010-04-08 16:00:04 +00:00
if item.is_capable(ItemCapabilities.AllowsLoop) and \
len(item.get_frames()) > 1:
2011-01-21 20:56:09 +00:00
self.toolbar.makeWidgetsVisible(self.loopList)
2010-04-08 16:00:04 +00:00
if item.is_media():
2011-01-21 20:56:09 +00:00
self.toolbar.setVisible(False)
2011-01-22 08:59:46 +00:00
self.mediabar.setVisible(True)
def enablePreviewToolBar(self, item):
"""
Allows the Preview toolbar to be customised
"""
2011-01-21 20:56:09 +00:00
self.toolbar.setVisible(True)
2011-01-22 08:59:46 +00:00
self.mediabar.setVisible(False)
2011-01-21 20:56:09 +00:00
self.toolbar.makeWidgetsInvisible(self.songEditList)
if item.is_capable(ItemCapabilities.AllowsEdit) and item.from_plugin:
2011-01-21 20:56:09 +00:00
self.toolbar.makeWidgetsVisible(self.songEditList)
elif item.is_media():
2011-01-21 20:56:09 +00:00
self.toolbar.setVisible(False)
2011-01-22 08:59:46 +00:00
self.mediabar.setVisible(True)
2009-11-09 20:27:25 +00:00
self.volumeSlider.setAudioOutput(self.audio)
2010-03-13 15:11:31 +00:00
def refreshServiceItem(self):
"""
Method to update the service item if the screen has changed
"""
log.debug(u'refreshServiceItem live = %s' % self.isLive)
if self.serviceItem.is_text() or self.serviceItem.is_image():
item = self.serviceItem
item.render()
self._processItem(item, self.selectedRow)
2010-03-13 15:11:31 +00:00
def addServiceItem(self, item):
"""
Method to install the service item into the controller
Called by plugins
"""
log.debug(u'addServiceItem live = %s' % self.isLive)
2009-08-23 20:15:05 +00:00
item.render()
2009-10-24 18:11:02 +00:00
slideno = 0
if self.songEdit:
slideno = self.selectedRow
2009-10-24 18:11:02 +00:00
self.songEdit = False
self._processItem(item, slideno)
2009-10-24 18:11:02 +00:00
def replaceServiceManagerItem(self, item):
"""
Replacement item following a remote edit
"""
if item.__eq__(self.serviceItem):
2011-01-21 20:53:08 +00:00
self._processItem(item, self.previewListWidget.currentRow())
def addServiceManagerItem(self, item, slideno):
"""
Method to install the service item into the controller and
2009-11-13 17:42:51 +00:00
request the correct toolbar for the plugin.
Called by ServiceManager
"""
log.debug(u'addServiceManagerItem live = %s' % self.isLive)
# If no valid slide number is specified we take the first one.
if slideno == -1:
slideno = 0
2010-07-25 07:21:10 +00:00
# If service item is the same as the current on only change slide
2010-03-21 15:08:46 +00:00
if item.__eq__(self.serviceItem):
2011-02-04 03:31:06 +00:00
self.__checkUpdateSelectedSlide(slideno)
2010-03-21 15:08:46 +00:00
self.onSlideSelected()
return
self._processItem(item, slideno)
def _processItem(self, serviceItem, slideno):
"""
Loads a ServiceItem into the system from ServiceManager
Display the slide number passed
"""
log.debug(u'processManagerItem live = %s' % self.isLive)
2010-05-05 19:14:48 +00:00
self.onStopLoop()
2010-07-25 07:21:10 +00:00
# If old item was a command tell it to stop
if self.serviceItem:
if self.serviceItem.is_command():
Receiver.send_message(u'%s_stop' %
self.serviceItem.name.lower(), [serviceItem, self.isLive])
if self.serviceItem.is_media():
self.onMediaClose()
if self.isLive:
if serviceItem.is_capable(ItemCapabilities.ProvidesOwnDisplay):
self._forceUnblank()
2011-01-22 08:59:46 +00:00
blanked = self.blankScreen.isChecked()
else:
blanked = False
2010-06-30 04:52:52 +00:00
Receiver.send_message(u'%s_start' % serviceItem.name.lower(),
[serviceItem, self.isLive, blanked, slideno])
self.slideList = {}
2011-02-07 22:07:48 +00:00
width = self.parent.controlSplitter.sizes()[self.split]
self.serviceItem = serviceItem
2011-01-21 20:53:08 +00:00
self.previewListWidget.clear()
self.previewListWidget.setRowCount(0)
self.previewListWidget.setColumnWidth(0, width)
2009-12-06 16:50:13 +00:00
if self.isLive:
2011-01-22 08:59:46 +00:00
self.songMenu.menu().clear()
row = 0
text = []
for framenumber, frame in enumerate(self.serviceItem.get_frames()):
2011-01-21 20:53:08 +00:00
self.previewListWidget.setRowCount(
self.previewListWidget.rowCount() + 1)
2009-08-23 20:15:05 +00:00
item = QtGui.QTableWidgetItem()
2010-05-15 06:44:36 +00:00
slideHeight = 0
if self.serviceItem.is_text():
if frame[u'verseTag']:
2011-02-17 19:46:01 +00:00
# These tags are already translated.
verse_def = frame[u'verseTag']
verse_def = u'%s%s' % (verse_def[0].upper(), verse_def[1:])
2011-02-18 16:37:41 +00:00
two_line_def = u'%s\n%s' % (verse_def[0], verse_def[1:])
row = two_line_def
2010-07-25 07:21:10 +00:00
if self.isLive:
if verse_def not in self.slideList:
self.slideList[verse_def] = framenumber
self.songMenu.menu().addAction(verse_def,
2010-07-25 07:21:10 +00:00
self.onSongBarHandler)
else:
row += 1
item.setText(frame[u'text'])
else:
label = QtGui.QLabel()
label.setMargin(4)
2009-09-15 19:06:40 +00:00
label.setScaledContents(True)
2010-10-24 06:26:07 +00:00
if self.serviceItem.is_command():
image = resize_image(frame[u'image'],
2010-12-03 18:56:12 +00:00
self.parent.renderManager.width,
self.parent.renderManager.height)
2010-10-24 06:26:07 +00:00
else:
2011-03-04 17:21:50 +00:00
# If current slide set background to image
if framenumber == slideno:
self.serviceItem.bg_image_bytes = \
self.parent.renderManager.image_manager. \
get_image_bytes(frame[u'title'])
2010-12-03 18:56:12 +00:00
image = self.parent.renderManager.image_manager. \
2011-01-12 19:31:46 +00:00
get_image(frame[u'title'])
label.setPixmap(QtGui.QPixmap.fromImage(image))
2011-01-21 20:53:08 +00:00
self.previewListWidget.setCellWidget(framenumber, 0, label)
2010-12-03 18:56:12 +00:00
slideHeight = width * self.parent.renderManager.screen_ratio
2010-03-30 19:01:23 +00:00
row += 1
text.append(unicode(row))
2011-01-21 20:53:08 +00:00
self.previewListWidget.setItem(framenumber, 0, item)
2010-05-15 06:44:36 +00:00
if slideHeight != 0:
2011-01-21 20:53:08 +00:00
self.previewListWidget.setRowHeight(framenumber, slideHeight)
self.previewListWidget.setVerticalHeaderLabels(text)
if self.serviceItem.is_text():
2011-01-21 20:53:08 +00:00
self.previewListWidget.resizeRowsToContents()
self.previewListWidget.setColumnWidth(0,
self.previewListWidget.viewport().size().width())
2011-02-01 00:33:50 +00:00
self.__updatePreviewSelection(slideno)
self.enableToolBar(serviceItem)
2010-07-17 08:59:15 +00:00
# Pass to display for viewing
self.display.buildHtml(self.serviceItem)
2010-07-26 16:42:19 +00:00
if serviceItem.is_media():
self.onMediaStart(serviceItem)
2009-08-23 20:15:05 +00:00
self.onSlideSelected()
2011-01-21 20:53:08 +00:00
self.previewListWidget.setFocus()
2010-05-10 18:19:45 +00:00
Receiver.send_message(u'slidecontroller_%s_started' % self.typePrefix,
2010-04-22 21:22:09 +00:00
[serviceItem])
2011-02-01 00:33:50 +00:00
def __updatePreviewSelection(self, slideno):
"""
Utility method to update the selected slide in the list.
"""
if slideno > self.previewListWidget.rowCount():
self.previewListWidget.selectRow(
self.previewListWidget.rowCount() - 1)
else:
2011-02-04 03:31:06 +00:00
self.__checkUpdateSelectedSlide(slideno)
2011-02-01 00:33:50 +00:00
def onTextRequest(self):
"""
Return the text for the current item in controller
"""
data = []
2010-04-29 22:52:23 +00:00
if self.serviceItem:
for framenumber, frame in enumerate(self.serviceItem.get_frames()):
2010-05-15 06:44:36 +00:00
dataItem = {}
2010-04-29 22:52:23 +00:00
if self.serviceItem.is_text():
2010-05-15 06:44:36 +00:00
dataItem[u'tag'] = unicode(frame[u'verseTag'])
dataItem[u'text'] = unicode(frame[u'html'])
2010-04-29 22:52:23 +00:00
else:
2010-05-15 06:44:36 +00:00
dataItem[u'tag'] = unicode(framenumber)
dataItem[u'text'] = u''
dataItem[u'selected'] = \
2011-01-21 20:53:08 +00:00
(self.previewListWidget.currentRow() == framenumber)
2010-05-15 06:44:36 +00:00
data.append(dataItem)
2010-05-05 19:14:48 +00:00
Receiver.send_message(u'slidecontroller_%s_text_response'
2010-05-10 18:19:45 +00:00
% self.typePrefix, data)
2010-07-24 16:55:06 +00:00
# Screen event methods
2009-08-23 20:15:05 +00:00
def onSlideSelectedFirst(self):
"""
Go to the first slide.
"""
if not self.serviceItem:
return
if self.serviceItem.is_command():
2010-09-17 20:32:00 +00:00
Receiver.send_message(u'%s_first' % self.serviceItem.name.lower(),
[self.serviceItem, self.isLive])
self.updatePreview()
else:
2011-01-21 20:53:08 +00:00
self.previewListWidget.selectRow(0)
self.onSlideSelected()
2009-08-23 20:15:05 +00:00
def onSlideSelectedIndex(self, message):
"""
Go to the requested slide
"""
index = int(message[0])
if not self.serviceItem:
return
if self.serviceItem.is_command():
2010-09-17 20:32:00 +00:00
Receiver.send_message(u'%s_slide' % self.serviceItem.name.lower(),
[self.serviceItem, self.isLive, index])
self.updatePreview()
else:
2011-02-04 03:31:06 +00:00
self.__checkUpdateSelectedSlide(index)
self.onSlideSelected()
2010-06-13 19:41:11 +00:00
def mainDisplaySetBackground(self):
"""
Allow the main display to blank the main display at startup time
"""
log.debug(u'mainDisplaySetBackground live = %s' % self.isLive)
display_type = QtCore.QSettings().value(
self.parent.generalSettingsSection + u'/screen blank',
QtCore.QVariant(u'')).toString()
2010-07-24 16:55:06 +00:00
if not self.display.primary:
# Order done to handle initial conversion
if display_type == u'themed':
self.onThemeDisplay(True)
elif display_type == u'hidden':
self.onHideDisplay(True)
else:
self.onBlankDisplay(True)
def onSlideBlank(self):
"""
Handle the slidecontroller blank event
"""
self.onBlankDisplay(True)
def onSlideUnblank(self):
"""
Handle the slidecontroller unblank event
"""
self.onBlankDisplay(False)
2010-04-29 19:33:45 +00:00
def onBlankDisplay(self, checked):
2010-01-24 16:28:18 +00:00
"""
2010-06-23 17:37:01 +00:00
Handle the blank screen button actions
2010-01-24 16:28:18 +00:00
"""
log.debug(u'onBlankDisplay %s' % checked)
2011-01-22 08:59:46 +00:00
self.hideMenu.setDefaultAction(self.blankScreen)
self.blankScreen.setChecked(checked)
self.themeScreen.setChecked(False)
2010-08-05 19:01:24 +00:00
if self.screens.display_count > 1:
2011-01-22 08:59:46 +00:00
self.desktopScreen.setChecked(False)
2010-04-29 19:33:45 +00:00
if checked:
2010-04-29 20:56:27 +00:00
Receiver.send_message(u'maindisplay_hide', HideMode.Blank)
QtCore.QSettings().setValue(
self.parent.generalSettingsSection + u'/screen blank',
QtCore.QVariant(u'blanked'))
2010-04-29 19:33:45 +00:00
else:
Receiver.send_message(u'maindisplay_show')
QtCore.QSettings().remove(
self.parent.generalSettingsSection + u'/screen blank')
self.blankPlugin(checked)
self.updatePreview()
2010-04-29 19:33:45 +00:00
def onThemeDisplay(self, checked):
"""
Handle the Theme screen button
"""
log.debug(u'onThemeDisplay %s' % checked)
2011-01-22 08:59:46 +00:00
self.hideMenu.setDefaultAction(self.themeScreen)
self.blankScreen.setChecked(False)
self.themeScreen.setChecked(checked)
2010-08-05 19:01:24 +00:00
if self.screens.display_count > 1:
2011-01-22 08:59:46 +00:00
self.desktopScreen.setChecked(False)
2010-04-29 19:33:45 +00:00
if checked:
2010-04-29 20:56:27 +00:00
Receiver.send_message(u'maindisplay_hide', HideMode.Theme)
QtCore.QSettings().setValue(
self.parent.generalSettingsSection + u'/screen blank',
QtCore.QVariant(u'themed'))
2010-04-29 19:33:45 +00:00
else:
Receiver.send_message(u'maindisplay_show')
QtCore.QSettings().remove(
self.parent.generalSettingsSection + u'/screen blank')
self.blankPlugin(checked)
self.updatePreview()
2010-04-29 19:33:45 +00:00
def onHideDisplay(self, checked):
"""
Handle the Hide screen button
"""
log.debug(u'onHideDisplay %s' % checked)
2011-01-22 08:59:46 +00:00
self.hideMenu.setDefaultAction(self.desktopScreen)
self.blankScreen.setChecked(False)
self.themeScreen.setChecked(False)
# On valid if more than 1 display
if self.screens.display_count <= 1:
return
2011-01-22 08:59:46 +00:00
self.desktopScreen.setChecked(checked)
2010-04-29 19:33:45 +00:00
if checked:
2010-04-29 20:56:27 +00:00
Receiver.send_message(u'maindisplay_hide', HideMode.Screen)
QtCore.QSettings().setValue(
self.parent.generalSettingsSection + u'/screen blank',
QtCore.QVariant(u'hidden'))
else:
Receiver.send_message(u'maindisplay_show')
QtCore.QSettings().remove(
self.parent.generalSettingsSection + u'/screen blank')
self.hidePlugin(checked)
self.updatePreview()
2010-04-30 15:41:48 +00:00
def blankPlugin(self, blank):
2009-08-23 20:15:05 +00:00
"""
Blank the display screen within a plugin if required.
2009-08-23 20:15:05 +00:00
"""
log.debug(u'blankPlugin %s ', blank)
if self.serviceItem is not None:
2010-04-30 15:41:48 +00:00
if blank:
Receiver.send_message(u'%s_blank'
% self.serviceItem.name.lower(),
2010-04-16 07:31:01 +00:00
[self.serviceItem, self.isLive])
2010-03-19 23:02:23 +00:00
else:
2010-04-30 15:41:48 +00:00
Receiver.send_message(u'%s_unblank'
% self.serviceItem.name.lower(),
2010-04-16 07:31:01 +00:00
[self.serviceItem, self.isLive])
2009-08-23 20:15:05 +00:00
def hidePlugin(self, hide):
"""
Tell the plugin to hide the display screen.
"""
log.debug(u'hidePlugin %s ', hide)
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])
2009-08-23 20:15:05 +00:00
def onSlideSelected(self):
"""
Generate the preview when you click on a slide.
if this is the Live Controller also display on the screen
"""
2011-01-21 20:53:08 +00:00
row = self.previewListWidget.currentRow()
self.selectedRow = 0
2011-01-21 20:53:08 +00:00
if row > -1 and row < self.previewListWidget.rowCount():
2010-11-01 19:22:00 +00:00
if self.serviceItem.is_command():
if self.isLive:
2010-11-03 18:35:56 +00:00
Receiver.send_message(
u'%s_slide' % self.serviceItem.name.lower(),
2010-11-01 19:22:00 +00:00
[self.serviceItem, self.isLive, row])
self.updatePreview()
else:
2010-10-23 17:37:10 +00:00
toDisplay = self.serviceItem.get_rendered_frame(row)
2010-07-17 08:59:15 +00:00
if self.serviceItem.is_text():
2010-10-23 17:37:10 +00:00
frame = self.display.text(toDisplay)
2010-07-17 08:59:15 +00:00
else:
2010-10-23 17:37:10 +00:00
frame = self.display.image(toDisplay)
2011-03-04 17:21:50 +00:00
# reset the store used to display first image
self.serviceItem.bg_image_bytes = None
2011-01-22 08:59:46 +00:00
self.slidePreview.setPixmap(QtGui.QPixmap.fromImage(frame))
self.selectedRow = row
2010-05-10 18:19:45 +00:00
Receiver.send_message(u'slidecontroller_%s_changed' % self.typePrefix,
2010-04-29 22:52:23 +00:00
row)
2009-10-24 13:07:41 +00:00
def onSlideChange(self, row):
"""
The slide has been changed. Update the slidecontroller accordingly
"""
2011-02-04 03:31:06 +00:00
self.__checkUpdateSelectedSlide(row)
self.updatePreview()
2010-05-10 18:19:45 +00:00
Receiver.send_message(u'slidecontroller_%s_changed' % self.typePrefix,
2010-04-29 22:52:23 +00:00
row)
2009-08-23 20:15:05 +00:00
def updatePreview(self):
2011-01-22 19:32:02 +00:00
"""
This updates the preview frame, for example after changing a slide or
using *Blank to Theme*.
"""
log.debug(u'updatePreview %s ' % self.screens.current[u'primary'])
if not self.screens.current[u'primary'] and self.serviceItem and \
self.serviceItem.is_capable(ItemCapabilities.ProvidesOwnDisplay):
2010-05-29 19:50:50 +00:00
# Grab now, but try again in a couple of seconds if slide change
# is slow
QtCore.QTimer.singleShot(0.5, self.grabMainDisplay)
QtCore.QTimer.singleShot(2.5, self.grabMainDisplay)
else:
2011-01-22 08:59:46 +00:00
self.slidePreview.setPixmap(
QtGui.QPixmap.fromImage(self.display.preview()))
def grabMainDisplay(self):
2011-01-22 19:32:02 +00:00
"""
Creates an image of the current screen and updates the preview frame.
"""
winid = QtGui.QApplication.desktop().winId()
rect = self.screens.current[u'size']
winimg = QtGui.QPixmap.grabWindow(winid, rect.x(),
rect.y(), rect.width(), rect.height())
2011-01-22 08:59:46 +00:00
self.slidePreview.setPixmap(winimg)
2009-08-23 20:15:05 +00:00
def onSlideSelectedNextNoloop(self):
self.onSlideSelectedNext(False)
def onSlideSelectedNext(self, loop=True):
2009-08-23 20:15:05 +00:00
"""
Go to the next slide.
"""
2009-11-30 18:29:22 +00:00
if not self.serviceItem:
return
Receiver.send_message(u'%s_next' % self.serviceItem.name.lower(),
2010-04-16 07:31:01 +00:00
[self.serviceItem, self.isLive])
if self.serviceItem.is_command() and self.isLive:
self.updatePreview()
2009-09-05 19:58:02 +00:00
else:
2011-01-21 20:53:08 +00:00
row = self.previewListWidget.currentRow() + 1
if row == self.previewListWidget.rowCount():
if loop:
row = 0
else:
2011-01-17 22:25:05 +00:00
Receiver.send_message('servicemanager_next_item')
return
2011-02-04 03:31:06 +00:00
self.__checkUpdateSelectedSlide(row)
2009-09-05 19:58:02 +00:00
self.onSlideSelected()
2009-08-23 20:15:05 +00:00
def onSlideSelectedPreviousNoloop(self):
self.onSlideSelectedPrevious(False)
def onSlideSelectedPrevious(self, loop=True):
2009-08-23 20:15:05 +00:00
"""
Go to the previous slide.
"""
if not self.serviceItem:
return
Receiver.send_message(u'%s_previous' % self.serviceItem.name.lower(),
2010-04-30 21:00:17 +00:00
[self.serviceItem, self.isLive])
if self.serviceItem.is_command() and self.isLive:
self.updatePreview()
2009-09-06 19:23:57 +00:00
else:
2011-01-21 20:53:08 +00:00
row = self.previewListWidget.currentRow() - 1
2009-09-06 19:23:57 +00:00
if row == -1:
if loop:
2011-01-21 20:53:08 +00:00
row = self.previewListWidget.rowCount() - 1
else:
row = 0
2011-02-04 03:31:06 +00:00
self.__checkUpdateSelectedSlide(row)
2009-09-06 19:23:57 +00:00
self.onSlideSelected()
2009-08-23 20:15:05 +00:00
2011-02-04 03:31:06 +00:00
def __checkUpdateSelectedSlide(self, row):
if row + 1 < self.previewListWidget.rowCount():
self.previewListWidget.scrollToItem(
self.previewListWidget.item(row + 1, 0))
self.previewListWidget.selectRow(row)
2009-08-23 20:15:05 +00:00
def onSlideSelectedLast(self):
"""
Go to the last slide.
"""
if not self.serviceItem:
return
Receiver.send_message(u'%s_last' % self.serviceItem.name.lower(),
2010-04-16 07:31:01 +00:00
[self.serviceItem, self.isLive])
if self.serviceItem.is_command():
self.updatePreview()
else:
2011-01-21 20:53:08 +00:00
self.previewListWidget.selectRow(
self.previewListWidget.rowCount() - 1)
self.onSlideSelected()
def onStartLoop(self):
2009-08-24 05:10:04 +00:00
"""
Start the timer loop running and store the timer id
2009-08-24 05:10:04 +00:00
"""
2011-01-21 20:53:08 +00:00
if self.previewListWidget.rowCount() > 1:
2009-09-21 17:56:36 +00:00
self.timer_id = self.startTimer(
2011-02-01 18:05:59 +00:00
int(self.delaySpinBox.value()) * 1000)
2011-01-21 20:56:09 +00:00
self.toolbar.actions[u'Stop Loop'].setVisible(True)
self.toolbar.actions[u'Start Loop'].setVisible(False)
2009-08-24 05:10:04 +00:00
def onStopLoop(self):
"""
Stop the timer loop running
2009-08-24 05:10:04 +00:00
"""
2010-05-05 19:14:48 +00:00
if self.timer_id != 0:
self.killTimer(self.timer_id)
self.timer_id = 0
2011-01-21 20:56:09 +00:00
self.toolbar.actions[u'Start Loop'].setVisible(True)
self.toolbar.actions[u'Stop Loop'].setVisible(False)
2010-05-05 19:14:48 +00:00
2009-08-24 05:10:04 +00:00
def timerEvent(self, event):
"""
If the timer event is for this window select next slide
"""
2009-08-24 05:10:04 +00:00
if event.timerId() == self.timer_id:
self.onSlideSelectedNext()
2009-10-24 13:07:41 +00:00
def onEditSong(self):
2010-04-29 20:56:27 +00:00
"""
From the preview display requires the service Item to be editied
"""
2009-10-24 18:11:02 +00:00
self.songEdit = True
2010-04-22 21:22:09 +00:00
Receiver.send_message(u'%s_edit' % self.serviceItem.name.lower(),
u'P:%s' % self.serviceItem.edit_id)
2009-10-24 13:07:41 +00:00
def onGoLiveClick(self):
"""
triggered by clicking the Preview slide items
"""
if QtCore.QSettings().value(u'advanced/double click live',
QtCore.QVariant(False)).toBool():
self.onGoLive()
def onGoLive(self):
"""
If preview copy slide item to live
"""
2011-01-21 20:53:08 +00:00
row = self.previewListWidget.currentRow()
if row > -1 and row < self.previewListWidget.rowCount():
2010-12-11 20:49:50 +00:00
self.parent.liveController.addServiceManagerItem(
self.serviceItem, row)
2009-11-09 20:27:25 +00:00
def onMediaStart(self, item):
2010-04-29 20:56:27 +00:00
"""
Respond to the arrival of a media service item
"""
log.debug(u'SlideController onMediaStart')
2010-10-01 22:47:37 +00:00
file = os.path.join(item.get_frame_path(), item.get_frame_title())
if self.isLive:
2010-08-04 19:09:43 +00:00
self.display.video(file, self.volume)
2010-08-02 05:16:07 +00:00
self.volumeSlider.setValue(self.volume)
else:
self.mediaObject.stop()
self.mediaObject.clearQueue()
self.mediaObject.setCurrentSource(Phonon.MediaSource(file))
2010-04-08 09:15:40 +00:00
self.seekSlider.setMediaObject(self.mediaObject)
self.seekSlider.show()
self.onMediaPlay()
2009-11-09 20:27:25 +00:00
2010-08-02 05:16:07 +00:00
def mediaVolume(self):
"""
Respond to the release of Volume Slider
"""
log.debug(u'SlideController mediaVolume')
self.volume = self.volumeSlider.value()
self.display.videoVolume(self.volume)
def onMediaPause(self):
2010-04-29 20:56:27 +00:00
"""
Respond to the Pause from the media Toolbar
"""
log.debug(u'SlideController onMediaPause')
2010-04-22 21:22:09 +00:00
if self.isLive:
2010-08-01 16:46:24 +00:00
self.display.videoPause()
2010-04-22 21:22:09 +00:00
else:
2009-11-09 20:27:25 +00:00
self.mediaObject.pause()
def onMediaPlay(self):
2010-04-29 20:56:27 +00:00
"""
Respond to the Play from the media Toolbar
"""
log.debug(u'SlideController onMediaPlay')
2010-04-22 21:22:09 +00:00
if self.isLive:
2010-08-01 16:46:24 +00:00
self.display.videoPlay()
2010-04-22 21:22:09 +00:00
else:
2011-01-22 08:59:46 +00:00
self.slidePreview.hide()
2009-11-09 20:27:25 +00:00
self.video.show()
self.mediaObject.play()
def onMediaStop(self):
2010-04-29 20:56:27 +00:00
"""
Respond to the Stop from the media Toolbar
"""
log.debug(u'SlideController onMediaStop')
2010-04-22 21:22:09 +00:00
if self.isLive:
2010-08-01 16:46:24 +00:00
self.display.videoStop()
2010-04-22 21:22:09 +00:00
else:
2009-11-09 20:27:25 +00:00
self.mediaObject.stop()
self.video.hide()
2011-01-22 08:59:46 +00:00
self.slidePreview.clear()
self.slidePreview.show()
2010-10-15 15:33:06 +00:00
def onMediaClose(self):
"""
Respond to a request to close the Video
"""
log.debug(u'SlideController onMediaStop')
if self.isLive:
self.display.resetVideo()
else:
self.mediaObject.stop()
self.mediaObject.clearQueue()
self.video.hide()
2011-01-22 08:59:46 +00:00
self.slidePreview.clear()
self.slidePreview.show()
def _forceUnblank(self):
"""
Used by command items which provide their own displays to reset the
screen hide attributes
"""
2011-01-22 08:59:46 +00:00
if self.blankScreen.isChecked:
self.blankScreen.setChecked(False)
self.hideMenu.setDefaultAction(self.blankScreen)
QtCore.QSettings().remove(
self.parent.generalSettingsSection + u'/screen blank')
2011-01-22 08:59:46 +00:00
if self.themeScreen.isChecked:
self.themeScreen.setChecked(False)
self.hideMenu.setDefaultAction(self.themeScreen)
if self.screens.display_count > 1:
2011-01-22 08:59:46 +00:00
if self.desktopScreen.isChecked:
self.desktopScreen.setChecked(False)
self.hideMenu.setDefaultAction(self.desktopScreen)