Inherit from presentationcontrollers plus powerpoint

This commit is contained in:
Jonathan Corwin 2009-09-26 21:51:05 +01:00
parent 96e3f7bce6
commit c01ed3eb84
6 changed files with 321 additions and 332 deletions

View File

@ -22,13 +22,10 @@
# Temple Place, Suite 330, Boston, MA 02111-1307 USA #
###############################################################################
import os
from presentationcontroller import PresentationController
from impresscontroller import ImpressController
if os.name == u'nt':
#from powerpointcontroller import PowerpointController
from pptviewcontroller import PptviewController
from powerpointcontroller import PowerpointController
from pptviewcontroller import PptviewController
from messagelistener import MessageListener
from mediaitem import PresentationMediaItem
from presentationtab import PresentationTab

View File

@ -36,7 +36,10 @@ else:
from PyQt4 import QtCore
class ImpressController(object):
from presentationcontroller import PresentationController
class ImpressController(PresentationController):
"""
Class to control interactions with Impress presentations.
It creates the runtime environment, loads and closes the presentation as
@ -45,14 +48,29 @@ class ImpressController(object):
global log
log = logging.getLogger(u'ImpressController')
def __init__(self):
def __init__(self, plugin):
"""
Initialise the class
"""
log.debug(u'Initialising')
PresentationController.__init__(self, plugin, u'Impress')
self.process = None
self.document = None
self.presentation = None
self.startOpenoffice()
self.controller = None
def startOpenoffice(self):
def is_available(self):
"""
PPT Viewer is able to run on this machine
"""
log.debug(u'is_available')
try:
self.start_process()
return True
except:
return False
def start_process(self):
"""
Loads a running version of OpenOffice in the background.
It is not displayed to the user but is available to the UNO interface
@ -71,7 +89,7 @@ class ImpressController(object):
Called at system exit to clean up any running presentations
"""
log.debug(u'Kill')
self.closePresentation()
self.close_presentation()
def load_presentation(self, presentation):
"""
@ -86,10 +104,10 @@ class ImpressController(object):
"""
log.debug(u'LoadPresentation')
if os.name == u'nt':
desktop = self.getCOMDesktop()
desktop = self.get_com_desktop()
url = u'file:///' + presentation.replace(u'\\', u'/').replace(u':', u'|').replace(u' ', u'%20')
else:
desktop = self.getUNODesktop()
desktop = self.get_uno_desktop()
url = uno.systemPathToFileUrl(presentation)
if desktop is None:
return
@ -100,19 +118,19 @@ class ImpressController(object):
url, "_blank", 0, properties)
self.presentation = self.document.getPresentation()
self.presentation.start()
self.xSlideShowController = \
self.controller = \
desktop.getCurrentComponent().Presentation.getController()
except:
log.exception(u'Failed to load presentation')
def getUNODesktop(self):
def get_uno_desktop(self):
log.debug(u'getUNODesktop')
ctx = None
loop = 0
context = uno.getComponentContext()
resolver = context.ServiceManager.createInstanceWithContext(
u'com.sun.star.bridge.UnoUrlResolver', context)
while ctx == None and loop < 3:
while ctx is None and loop < 3:
try:
ctx = resolver.resolve(u'uno:socket,host=localhost,port=2002;urp;StarOffice.ComponentContext')
except:
@ -127,7 +145,7 @@ class ImpressController(object):
log.exception(u'Failed to get UNO desktop')
return None
def getCOMDesktop(self):
def get_com_desktop(self):
log.debug(u'getCOMDesktop')
try:
smgr = Dispatch("com.sun.star.ServiceManager")
@ -150,43 +168,45 @@ class ImpressController(object):
self.document.dispose()
self.document = None
def isActive(self):
def is_loaded(self):
return self.presentation is not None and self.document is not None
def is_active(self):
if not self.is_loaded():
return False
return self.presentation.isRunning() and self.presentation.isActive()
def resume(self):
def unblank_screen(self):
return self.presentation.resume()
def pause(self):
return self.presentation.pause()
def blankScreen(self):
def blank_screen(self):
self.presentation.blankScreen(0)
def stop(self):
def stop_presentation(self):
self.presentation.deactivate()
# self.presdoc.end()
def go(self):
def start_presentation(self):
self.presentation.activate()
# self.presdoc.start()
def getSlideNumber(self):
def get_slide_number(self):
return self.presentation.getCurrentSlideIndex
def setSlideNumber(self, slideno):
def goto_slide(self, slideno):
self.presentation.gotoSlideIndex(slideno)
slideNumber = property(getSlideNumber, setSlideNumber)
def next_step(self):
"""
Triggers the next effect of slide on the running presentation
"""
self.xSlideShowController.gotoNextEffect()
self.controller.gotoNextEffect()
def previous_step(self):
"""
Triggers the previous slide on the running presentation
"""
self.xSlideShowController.gotoPreviousSlide()
self.controller.gotoPreviousSlide()
# def get_slide_preview_file(self, slide_no):

View File

@ -21,148 +21,161 @@
# with this program; if not, write to the Free Software Foundation, Inc., 59 #
# Temple Place, Suite 330, Boston, MA 02111-1307 USA #
###############################################################################
try:
import os
import logging
if os.name == u'nt':
from win32com.client import Dispatch
except:
pass
from presentationcontroller import PresentationController
# PPT API documentation:
# http://msdn.microsoft.com/en-us/library/aa269321(office.10).aspx
class PowerPointApp(object):
def __init__(self):
class PowerpointController(PresentationController):
"""
Class to control interactions with PowerPoint Presentations
It creates the runtime Environment , Loads the and Closes the Presentation
As well as triggering the correct activities based on the users input
"""
global log
log = logging.getLogger(u'PowerpointController')
def __init__(self, plugin):
"""
Initialise the class
"""
log.debug(u'Initialising')
PresentationController.__init__(self, plugin, u'Powerpoint')
self.process = None
self.document = None
self.presentation = None
self.startPowerpoint()
def startPowerpoint(self):
def is_available(self):
"""
PowerPoint is able to run on this machine
"""
log.debug(u'is_available')
if os.name != u'nt':
return False
try:
self._app = Dispatch(u'PowerPoint.Application')
self.start_process()
return True
except:
self._app = None
return
self._app.Visible = True
self._app.WindowState = 2
def getApp(self):
if self._app == None:
self.createApp()
if self._app == None:
return None
if self._app.Windows.Count == 0:
self.createApp()
return self._app
app = property(getApp)
def quit(self):
self._app.Quit()
self._app = None
class PowerPointPres(object):
def __init__(self, pptApp, filename):
self.pptApp = pptApp
self.filename = filename
self.open()
def getPres(self):
if self._pres == None:
for p in self.pptApp.app.Presentations:
if p.FullName == self.filename:
self._pres = p
break
if self._pres != None:
try:
x = self._pres.Name
except:
self._pres = None
if self._pres == None:
self.openPres()
return self._pres
pres = property(getPres)
def open(self):
self.pptApp.app.Presentations.Open(self.filename, False, False, True)
self._pres = self.pptApp.app.Presentations(ppt.app.Presentations.Count)
def close(self):
self.pres.Close()
self._pres = None
def isActive(self):
if self.pres.SlideShowWindow == None:
return False
if self.pres.SlideShowWindow.View == None:
return False
return True
def resume(self):
self.pres.SlideShowSettings.Run()
self.pres.SlideShowWindow.View.State = 1
self.pres.SlideShowWindow.Activate()
if os.name == u'nt':
def start_process(self):
"""
Loads PowerPoint process
"""
self.process = Dispatch(u'PowerPoint.Application')
self.process.Visible = True
self.process.WindowState = 2
def pause(self):
if self.isActive():
self.pres.SlideShowWindow.View.State = 2
def is_loaded(self):
"""
Returns true if a presentation is loaded
"""
if self.process is None:
return False
if self.process.Windows.Count == 0:
return False
def kill(self):
self.process.Quit()
self.process = None
def blankScreen(self):
if self.isActive():
self.pres.SlideShowWindow.View.State = 3
def load_presentation(self, presentation):
"""
Called when a presentation is added to the SlideController.
It builds the environment, starts communcations with the background
OpenOffice task started earlier. If OpenOffice is not present is is
started. Once the environment is available the presentation is loaded
and started.
def stop(self):
if self.isActive():
self.pres.SlideShowWindow.View.Exit()
``presentation``
The file name of the presentations to run.
"""
self.filename = presentation
self.process.Presentations.Open(presentation, False, False, True)
self.presentation = self.process.Presentations(self.process.Presentations.Count)
self.start_presentation()
def close_presentation(self):
"""
Close presentation and clean up objects
Triggerent by new object being added to SlideController orOpenLP
being shut down
"""
self.presentation.Close()
self.presentation = None
def go(self):
self.pres.SlideShowSettings.Run()
def is_active(self):
"""
Returns true if a presentation is currently active
"""
if not self.is_loaded():
return False
if self.presentation.SlideShowWindow == None:
return False
if self.presentation.SlideShowWindow.View == None:
return False
return True
def getCurrentSlideIndex(self):
if self.isActive():
return self.pres.SlideShowWindow.View.CurrentShowPosition
else:
return -1
def unblank_screen(self):
"""
Unblanks (restores) the presentationn
"""
self.presentation.SlideShowSettings.Run()
self.presentation.SlideShowWindow.View.State = 1
self.presentation.SlideShowWindow.Activate()
def setCurrentSlideIndex(self, slideno):
if not self.isActive():
self.resume()
self.pres.SlideShowWindow.View.GotoSlide(slideno)
def blank_screen(self):
"""
Blanks the screen
"""
self.presentation.SlideShowWindow.View.State = 3
#currentSlideIndex = property(getSlideNumber, setSlideNumber)
def stop_presentation(self):
"""
Stops the current presentation and hides the output
"""
self.presentation.SlideShowWindow.View.Exit()
def nextStep(self):
if not self.isActive():
self.resume()
self.pres.SlideShowWindow.View.Next()
def start_presentation(self):
"""
Starts a presentation from the beginning
"""
self.presentation.SlideShowSettings.Run()
rendermanager = self.plugin.render_manager
rect = rendermanager.screen_list[rendermanager.current_display][u'size']
self.presentation.SlideShowWindow.Top = rect.y() / 20
self.presentation.SlideShowWindow.Height = rect.height() / 20
self.presentation.SlideShowWindow.Left = rect.x() / 20
self.presentation.SlideShowWindow.Width = rect.width() / 20
def prevStep(self):
if not self.isActive():
self.resume()
self.pres.SlideShowWindow.View.Previous()
def get_slide_number(self):
"""
Returns the current slide number
"""
return self.presentation.SlideShowWindow.View.CurrentShowPosition
def moveWindow(self, top, height, left, width):
if not self.isActive():
self.resume()
self.pres.SlideShowWindow.Top = top / 20
self.pres.SlideShowWindow.Height = height / 20
self.pres.SlideShowWindow.Left = left / 20
self.pres.SlideShowWindow.Width = width / 20
def get_slide_count(self):
"""
Returns total number of slides
"""
return self.presentation.Slides.Count
def goto_slide(self, slideno):
self.presentation.SlideShowWindow.View.GotoSlide(slideno)
class PowerPointSlide(object):
def __init__(self, pres, index):
self.pres = pres
self.slide = pres.Slides[index]
def next_step(self):
self.presentation.SlideShowWindow.View.Next()
def previous_step(self):
self.presentation.SlideShowWindow.View.Previous()
#def get_slide_preview_file(self, slide_no):
def preview(self):
if self.preview == None:
self.slide.Copy
# import win32clipboard as w
# import win32con
# w.OpenClipboard()
# self.preview = w.GetClipboardData.GetData(win32con.CF_BITMAP)
# w.CloseClipboard()
return self.preview

View File

@ -25,8 +25,9 @@
import os
import logging
from ctypes import *
from ctypes.wintypes import RECT
if os.name == u'nt':
from ctypes import *
from ctypes.wintypes import RECT
from presentationcontroller import PresentationController
@ -34,7 +35,7 @@ class PptviewController(PresentationController):
"""
Class to control interactions with PowerPOint Viewer Presentations
It creates the runtime Environment , Loads the and Closes the Presentation
As well as trigggering the correct activities based on the users input
As well as triggering the correct activities based on the users input
"""
global log
log = logging.getLogger(u'PptviewController')
@ -43,167 +44,148 @@ class PptviewController(PresentationController):
"""
Initialise the class
"""
log.debug(u'Initialised')
log.debug(u'Initialising')
PresentationController.__init__(self, plugin, u'Powerpoint Viewer')
self.process = None
self.pptid = None
self.thumbnailpath = os.path.join(plugin.config.get_data_path(),
u'pptview', u'thumbnails')
self.thumbprefix = u'slide'
self.start_process()
def start_process(self):
def is_available(self):
"""
Loads the PPTVIEWLIB library
PPT Viewer is able to run on this machine
"""
log.debug(u'start PPTView')
self.process = cdll.LoadLibrary(r'openlp\plugins\presentations\lib\pptviewlib\pptviewlib.dll')
def kill(self):
"""
Called at system exit to clean up any running presentations
"""
log.debug(u'Kill')
self.close_presentation()
def load_presentation(self, presentation):
"""
Called when a presentation is added to the SlideController.
It builds the environment, starts communcations with the background
OpenOffice task started earlier. If OpenOffice is not present is is
started. Once the environment is available the presentation is loaded
and started.
``presentation``
The file name of the presentations to run.
"""
log.debug(u'LoadPresentation')
if self.pptid >= 0:
self.close_presentation()
rendermanager = self.plugin.render_manager
#screen = rendermanager.screen_list[rendermanager.current_display]
# x? y?
rect = RECT(0, 0, rendermanager.width, rendermanager.height)
filename = str(presentation.replace(u'/', u'\\'));
log.debug(u'is_available')
if os.name != u'nt':
return False
try:
self.pptid = self.process.OpenPPT(filename, None, rect,
str(self.thumbnailpath))
self.start_process()
return True
except:
log.exception(u'Failed to load presentation')
return False
if os.name == u'nt':
def start_process(self):
"""
Loads the PPTVIEWLIB library
"""
log.debug(u'start PPTView')
self.process = cdll.LoadLibrary(r'openlp\plugins\presentations\lib\pptviewlib\pptviewlib.dll')
def close_presentation(self):
"""
Close presentation and clean up objects
Triggerent by new object being added to SlideController orOpenLP
being shut down
"""
if self.pptid < 0:
return
self.process.ClosePPT(self.pptid)
self.pptid = -1
def kill(self):
"""
Called at system exit to clean up any running presentations
"""
log.debug(u'Kill')
self.close_presentation()
def is_active(self):
"""
Returns true if a presentation is currently active
"""
return self.pptid >= 0
def load_presentation(self, presentation):
"""
Called when a presentation is added to the SlideController.
It builds the environment, starts communcations with the background
OpenOffice task started earlier. If OpenOffice is not present is is
started. Once the environment is available the presentation is loaded
and started.
def resume_presentation(self):
"""
Resumes a previously paused presentation
"""
if self.pptid < 0:
return
self.process.Resume(self.pptid)
``presentation``
The file name of the presentations to run.
"""
log.debug(u'LoadPresentation')
if self.pptid >= 0:
self.close_presentation()
rendermanager = self.plugin.render_manager
rect = rendermanager.screen_list[rendermanager.current_display][u'size']
rect = RECT(rect.x(), rect.y(), rect.right(), rect.bottom())
filename = str(presentation.replace(u'/', u'\\'));
try:
self.pptid = self.process.OpenPPT(filename, None, rect,
str(self.thumbnailpath))
except:
log.exception(u'Failed to load presentation')
def pause_presentation(self):
"""
Not implemented (pauses a presentation)
"""
return
def close_presentation(self):
"""
Close presentation and clean up objects
Triggerent by new object being added to SlideController orOpenLP
being shut down
"""
self.process.ClosePPT(self.pptid)
self.pptid = -1
def blank_screen(self):
"""
Blanks the screen
"""
if self.pptid < 0:
return
self.process.Blank(self.pptid)
def is_loaded(self):
"""
Returns true if a presentation is loaded
"""
return self.pptid >= 0
def is_active(self):
"""
Returns true if a presentation is currently active
"""
return self.pptid >= 0
def unblank_screen(self):
"""
Unblanks (restores) the presentationn
"""
if self.pptid < 0:
return
self.process.Unblank(self.pptid)
def blank_screen(self):
"""
Blanks the screen
"""
self.process.Blank(self.pptid)
def stop_presentation(self):
"""
Stops the current presentation and hides the output
"""
if self.pptid < 0:
return
self.process.Stop(self.pptid)
def unblank_screen(self):
"""
Unblanks (restores) the presentationn
"""
self.process.Unblank(self.pptid)
def start_presentation(self):
"""
Starts a presentation from the beginning
"""
if self.pptid < 0:
return
self.process.RestartShow(self.pptid)
def stop_presentation(self):
"""
Stops the current presentation and hides the output
"""
self.process.Stop(self.pptid)
def get_slide_number(self):
"""
Returns the current slide number
"""
if self.pptid < 0:
return 0
return self.process.GetCurrentSlide(self.pptid)
def start_presentation(self):
"""
Starts a presentation from the beginning
"""
self.process.RestartShow(self.pptid)
def get_slide_count(self):
"""
Returns total number of slides
"""
if self.pptid < 0:
return 0
return self.process.GetSlideCount(self.pptid)
def get_slide_number(self):
"""
Returns the current slide number
"""
return self.process.GetCurrentSlide(self.pptid)
def goto_slide(self, slideno):
"""
Moves to a specific slide in the presentation
"""
if self.pptid < 0:
return
self.process.GotoSlide(self.pptid, slideno)
def get_slide_count(self):
"""
Returns total number of slides
"""
return self.process.GetSlideCount(self.pptid)
def next_step(self):
"""
Triggers the next effect of slide on the running presentation
"""
if self.pptid < 0:
return
self.process.NextStep(self.pptid)
def goto_slide(self, slideno):
"""
Moves to a specific slide in the presentation
"""
self.process.GotoSlide(self.pptid, slideno)
def previous_step(self):
"""
Triggers the previous slide on the running presentation
"""
if self.pptid < 0:
return
self.process.PrevStep(self.pptid)
def next_step(self):
"""
Triggers the next effect of slide on the running presentation
"""
self.process.NextStep(self.pptid)
def get_slide_preview_file(self, slide_no):
"""
Returns an image path containing a preview for the requested slide
def previous_step(self):
"""
Triggers the previous slide on the running presentation
"""
self.process.PrevStep(self.pptid)
``slide_no``
The slide an image is required for, starting at 1
"""
if self.pptid < 0:
return
return os.path.join(self.thumbnailpath,
self.thumbprefix + slide_no + u'.bmp')
def get_slide_preview_file(self, slide_no):
"""
Returns an image path containing a preview for the requested slide
``slide_no``
The slide an image is required for, starting at 1
"""
return os.path.join(self.thumbnailpath,
self.thumbprefix + slide_no + u'.bmp')

View File

@ -31,7 +31,8 @@ class PresentationTab(SettingsTab):
"""
PresentationsTab is the Presentations settings tab in the settings dialog.
"""
def __init__(self):
def __init__(self, controllers):
self.controllers = controllers
SettingsTab.__init__(self,
translate(u'PresentationTab', u'Presentation'), u'Presentations')

View File

@ -28,14 +28,7 @@ import logging
from PyQt4 import QtCore, QtGui
from openlp.core.lib import Plugin
from openlp.plugins.presentations.lib import PresentationMediaItem, \
PresentationTab, ImpressController
if os.name == u'nt':
try:
from openlp.plugins.presentations.lib import PowerpointController
except:
pass
from openlp.plugins.presentations.lib import PptviewController
from openlp.plugins.presentations.lib import *
class PresentationPlugin(Plugin):
@ -57,7 +50,7 @@ class PresentationPlugin(Plugin):
"""
Create the settings Tab
"""
self.presentation_tab = PresentationTab()
self.presentation_tab = PresentationTab(self.controllers)
return self.presentation_tab
def get_media_manager_item(self):
@ -77,41 +70,24 @@ class PresentationPlugin(Plugin):
If Not do not install the plugin.
"""
log.debug('check_pre_conditions')
#Lets see if Impress is required (Default is Not wanted)
#Lets see if Powerpoint is required (Default is Not wanted)
controller = PowerpointController(self)
if int(self.config.get_config(
u'Impress', QtCore.Qt.Unchecked)) == QtCore.Qt.Checked:
try:
if os.name == u'nt':
#Check to see if we are Win32
from win32com.client import Dispatch
else:
#Check to see if we have uno installed
import uno
openoffice = ImpressController()
openoffice.name = u'Impress' # until controller updated
self.registerControllers(openoffice)
except:
log.exception(u'Failed to set up plugin for Impress')
if os.name == u'nt':
#Lets see if Powerpoint is required (Default is Not wanted)
if int(self.config.get_config(
u'Powerpoint', QtCore.Qt.Unchecked)) == QtCore.Qt.Checked:
try:
#Check to see if we are Win32
from win32com.client import Dispatch
powerpoint = PowerpointController()
powerpoint.name = u'Powerpoint' # until controller updated
self.registerControllers(powerpoint)
except:
log.exception(u'Failed to set up plugin for Powerpoint')
#Lets see if Powerpoint Viewer is required (Default is Not wanted)
if int(self.config.get_config(
u'Powerpoint Viewer', QtCore.Qt.Unchecked)) == QtCore.Qt.Checked:
try:
pptview = PptviewController(self)
self.registerControllers(pptview)
except:
log.exception(u'Failed to set up plugin for Powerpoint Viewer')
controller.name, QtCore.Qt.Unchecked)) == QtCore.Qt.Checked:
if controller.is_available():
self.registerControllers(controller)
#Lets see if Impress is required (Default is Not wanted)
controller = ImpressController(self)
if int(self.config.get_config(
controller.name, QtCore.Qt.Unchecked)) == QtCore.Qt.Checked:
if controller.is_available():
self.registerControllers(controller)
#Lets see if Powerpoint Viewer is required (Default is Not wanted)
controller = PptviewController(self)
if int(self.config.get_config(
controller.name, QtCore.Qt.Unchecked)) == QtCore.Qt.Checked:
if controller.is_available():
self.registerControllers(controller)
#If we have no available controllers disable plugin
if len(self.controllers) > 0:
return True