Beispiel #1
0
def themeHasConfigXML(style):
    themePath = Path(G.application.config.stylesDir / style)
    themeXMLFile = themePath.joinpath("config.xml")
    themeHasXML = False
    if themeXMLFile.exists():
        themeHasXML = True
    return themeHasXML
Beispiel #2
0
 def handleExport(self, client, exportType, filename):
     """
     Called by js. 
     Exports the current package to one of the above formats
     'exportType' can be one of 'singlePage' 'webSite' 'zipFile'
                  'textFile' or 'scorm'
     'filename' is a file for scorm pages, and a directory for websites
     """ 
     webDir     = Path(self.config.webDir)
     stylesDir  = webDir.joinpath('style', self.package.style)
     exportDir  = Path(filename).dirname()
     if exportDir and not exportDir.exists():
         client.alert(_(u'Cannot access directory named ') +
                      unicode(exportDir) +
                      _(u'. Please use ASCII names.'))
         return
     if exportType == 'singlePage':
         self.exportSinglePage(client, filename, webDir, stylesDir)
     elif exportType == 'webSite':
         self.exportWebSite(client, filename, stylesDir)
     elif exportType == 'zipFile':
         self.exportWebZip(client, filename, stylesDir)
     elif exportType == 'textFile':
         self.exportText(client, filename)
     elif exportType == "scorm":
         self.exportScorm(client, filename, stylesDir, "scorm1.2")
     elif exportType == "scorm2004":
         self.exportScorm(client, filename, stylesDir, "scorm2004")
     else:
         self.exportIMS(client, filename, stylesDir)
    def _process(self, request):
        """
        Delegates processing of args to blocks
        """  
        # Still need to call parent (mainpage.py) process
        # because the idevice pane needs to know that new idevices have been
        # added/edited..
        self.parent.process(request)
        if ("action" in request.args and 
            request.args["action"][0] == u"saveChange"):
            log.debug(u"process savachange:::::")
            self.package.save()
            log.debug(u"package name: " + self.package.name)
        for block in self.blocks:
            block.process(request)
        # now that each block and corresponding elements have been processed,
        # it's finally safe to remove any images/etc which made it into 
        # tinyMCE's previews directory, as they have now had their 
        # corresponding resources created:
        webDir     = Path(G.application.tempWebDir) 
        previewDir  = webDir.joinpath('previews')
        for root, dirs, files in os.walk(previewDir, topdown=False): 
            for name in files: 
                os.remove(os.path.join(root, name))

        log.debug(u"After authoringPage process" + repr(request.args))
Beispiel #4
0
def themeHasConfigXML(style):
    themePath = Path(G.application.config.stylesDir / style)
    themeXMLFile = themePath.joinpath("config.xml")
    themeHasXML = False
    if themeXMLFile.exists():
        themeHasXML = True
    return themeHasXML
Beispiel #5
0
    def __renderHeader(self):
		#TinyMCE lang (user preference)
        myPreferencesPage = self.webServer.preferences
        
        """Generates the header for AuthoringPage"""
        html  = common.docType()
        #################################################################################
        #################################################################################
        
        html += u'<html xmlns="http://www.w3.org/1999/xhtml" lang="'+myPreferencesPage.getSelectedLanguage()+'">\n'
        html += u'<head>\n'
        html += u"<link rel=\"stylesheet\" type=\"text/css\" href=\"/css/exe.css\" />"
        
        # Use the Style's base.css file if it exists
        themePath = Path(G.application.config.stylesDir/self.package.style)
        themeBaseCSS = themePath.joinpath("base.css")
        if themeBaseCSS.exists():
            html += u"<link rel=\"stylesheet\" type=\"text/css\" href=\"/style/%s/base.css\" />" % self.package.style
        else:
            html += u"<link rel=\"stylesheet\" type=\"text/css\" href=\"/style/base.css\" />"
            
        html += u"<link rel=\"stylesheet\" type=\"text/css\" href=\"/css/exe_wikipedia.css\" />"
        html += u"<link rel=\"stylesheet\" type=\"text/css\" href=\"/scripts/exe_effects/exe_effects.css\" />"
        html += u"<link rel=\"stylesheet\" type=\"text/css\" href=\"/scripts/exe_highlighter/exe_highlighter.css\" />"
        html += u"<link rel=\"stylesheet\" type=\"text/css\" href=\"/scripts/exe_games/exe_games.css\" />"
        html += u"<link rel=\"stylesheet\" type=\"text/css\" href=\"/style/%s/content.css\" />" % self.package.style
        if G.application.config.assumeMediaPlugins: 
            html += u"<script type=\"text/javascript\">var exe_assume_media_plugins = true;</script>\n"
        #JR: anado una variable con el estilo
        estilo = u'/style/%s/content.css' % self.package.style
        html += common.getJavaScriptStrings()
        # The games require additional strings
        html += common.getGamesJavaScriptStrings()
        html += u"<script type=\"text/javascript\">"
        html += u"var exe_style = '%s';top.exe_style = exe_style;" % estilo
        # editorpane.py uses exe_style_dirname to auto-select the current style (just a provisional solution)
        html += u"var exe_style_dirname = '%s'; top.exe_style_dirname = exe_style_dirname;" % self.package.style
        html += u"var exe_package_name='"+self.package.name+"';"
        html += 'var exe_export_format="'+common.getExportDocType()+'".toLowerCase();'
        html += 'var exe_editor_mode="'+myPreferencesPage.getEditorMode()+'";'
        html += 'var exe_editor_version="'+myPreferencesPage.getEditorVersion()+'";'
        html += '</script>\n'        
        html += u'<script type="text/javascript" src="../jsui/native.history.js"></script>\n'
        html += u'<script type="text/javascript" src="/scripts/authoring.js"></script>\n'
        html += u'<script type="text/javascript" src="/scripts/exe_jquery.js"></script>\n'
        html += u'<script type="text/javascript" src="/scripts/exe_lightbox/exe_lightbox.js"></script>\n'
        html += u'<script type="text/javascript" src="/scripts/exe_effects/exe_effects.js"></script>\n'
        html += u'<script type="text/javascript" src="/scripts/exe_highlighter/exe_highlighter.js"></script>\n'
        html += u'<script type="text/javascript" src="/scripts/exe_games/exe_games.js"></script>\n'
        html += u'<script type="text/javascript" src="/scripts/common.js"></script>\n'
        html += '<script type="text/javascript">document.write(unescape("%3Cscript src=\'" + eXeLearning_settings.wysiwyg_path + "\' type=\'text/javascript\'%3E%3C/script%3E"));</script>';
        html += '<script type="text/javascript">document.write(unescape("%3Cscript src=\'" + eXeLearning_settings.wysiwyg_settings_path + "\' type=\'text/javascript\'%3E%3C/script%3E"));</script>';
        html += u'<title>"+_("eXe : elearning XHTML editor")+"</title>\n'
        html += u'<meta http-equiv="content-type" content="text/html; '
        html += u' charset=UTF-8" />\n'
        style = G.application.config.styleStore.getStyle(self.package.style)
        if style.hasValidConfig:
            html += style.get_edition_extra_head()        
        html += u'</head>\n'
        return html
Beispiel #6
0
    def __renderHeader(self):
        #TinyMCE lang (user preference)
        myPreferencesPage = self.webServer.preferences
        """Generates the header for AuthoringPage"""
        html = common.docType()
        #################################################################################
        #################################################################################

        html += u'<html xmlns="http://www.w3.org/1999/xhtml" lang="' + myPreferencesPage.getSelectedLanguage(
        ) + '">\n'
        html += u'<head>\n'
        html += u"<link rel=\"stylesheet\" type=\"text/css\" href=\"/css/exe.css\" />"

        # Use the Style's base.css file if it exists
        themePath = Path(G.application.config.stylesDir / self.package.style)
        themeBaseCSS = themePath.joinpath("base.css")
        if themeBaseCSS.exists():
            html += u"<link rel=\"stylesheet\" type=\"text/css\" href=\"/style/%s/base.css\" />" % self.package.style
        else:
            html += u"<link rel=\"stylesheet\" type=\"text/css\" href=\"/style/base.css\" />"

        html += u"<link rel=\"stylesheet\" type=\"text/css\" href=\"/css/exe_wikipedia.css\" />"
        html += u"<link rel=\"stylesheet\" type=\"text/css\" href=\"/scripts/exe_effects/exe_effects.css\" />"
        html += u"<link rel=\"stylesheet\" type=\"text/css\" href=\"/scripts/exe_highlighter/exe_highlighter.css\" />"
        html += u"<link rel=\"stylesheet\" type=\"text/css\" href=\"/scripts/exe_games/exe_games.css\" />"
        html += u"<link rel=\"stylesheet\" type=\"text/css\" href=\"/style/%s/content.css\" />" % self.package.style
        if G.application.config.assumeMediaPlugins:
            html += u"<script type=\"text/javascript\">var exe_assume_media_plugins = true;</script>\n"
        #JR: anado una variable con el estilo
        estilo = u'/style/%s/content.css' % self.package.style
        html += common.getJavaScriptStrings()
        # The games require additional strings
        html += common.getGamesJavaScriptStrings()
        html += u"<script type=\"text/javascript\">"
        html += u"var exe_style = '%s';" % estilo
        html += u"var exe_package_name='" + self.package.name + "';"
        html += 'var exe_export_format="' + common.getExportDocType(
        ) + '".toLowerCase();'
        html += 'var exe_editor_mode="' + myPreferencesPage.getEditorMode(
        ) + '";'
        html += '</script>\n'
        html += u'<script type="text/javascript" src="../jsui/native.history.js"></script>\n'
        html += u'<script type="text/javascript" src="/scripts/authoring.js"></script>\n'
        html += u'<script type="text/javascript" src="/scripts/exe_jquery.js"></script>\n'
        html += u'<script type="text/javascript" src="/scripts/exe_lightbox/exe_lightbox.js"></script>\n'
        html += u'<script type="text/javascript" src="/scripts/exe_effects/exe_effects.js"></script>\n'
        html += u'<script type="text/javascript" src="/scripts/exe_highlighter/exe_highlighter.js"></script>\n'
        html += u'<script type="text/javascript" src="/scripts/exe_games/exe_games.js"></script>\n'
        html += u'<script type="text/javascript" src="/scripts/common.js"></script>\n'
        html += '<script type="text/javascript">document.write(unescape("%3Cscript src=\'" + eXeLearning_settings.wysiwyg_path + "\' type=\'text/javascript\'%3E%3C/script%3E"));</script>'
        html += '<script type="text/javascript">document.write(unescape("%3Cscript src=\'" + eXeLearning_settings.wysiwyg_settings_path + "\' type=\'text/javascript\'%3E%3C/script%3E"));</script>'
        html += u'<title>"+_("eXe : elearning XHTML editor")+"</title>\n'
        html += u'<meta http-equiv="content-type" content="text/html; '
        html += u' charset=UTF-8" />\n'
        style = G.application.config.styleStore.getStyle(self.package.style)
        if style.hasValidConfig:
            html += style.get_edition_extra_head()
        html += u'</head>\n'
        return html
Beispiel #7
0
 def handleTinyMCEmath(
     self,
     client,
     tinyMCEwin,
     tinyMCEwin_name,
     tinyMCEfield,
     latex_source,
     math_fontsize,
     preview_image_filename,
     preview_math_srcfile,
 ):
     """
     Based off of handleTinyMCEimageChoice(), 
     handleTinyMCEmath() is similar in that it places a .gif math image 
     (and a corresponding .tex LaTeX source file) into the previews dir.
     Rather than copying the image from a user-selected directory, though,
     this routine actually generates the math image using mimetex.
     """
     server_filename = ""
     callback_errors = ""
     errors = 0
     webDir = Path(G.application.tempWebDir)
     previewDir = webDir.joinpath("previews")
     if not previewDir.exists():
         log.debug("image previews directory does not yet exist; " + "creating as %s " % previewDir)
         previewDir.makedirs()
     elif not previewDir.isdir():
         client.alert(_(u"Preview directory %s is a file, cannot replace it") % previewDir)
         log.error(
             "Couldn't preview tinyMCE-chosen image: " + "Preview dir %s is a file, cannot replace it" % previewDir
         )
         callback_errors = "Preview dir is a file, cannot replace"
         errors += 1
     if latex_source <> "":
         math_filename = previewDir.joinpath(preview_math_srcfile)
         math_filename_str = math_filename.abspath().encode("utf-8")
         log.info("handleTinyMCEmath: using LaTeX source: " + latex_source)
         log.debug("writing LaTeX source into '" + math_filename_str + "'.")
         math_file = open(math_filename, "wb")
         math_file.write(latex_source)
         math_file.flush()
         math_file.close()
         try:
             use_latex_sourcefile = math_filename_str
             tempFileName = compile(use_latex_sourcefile, math_fontsize, latex_is_file=True)
         except Exception, e:
             client.alert(_("MimeTeX compile failed!\n%s" % str(e)))
             log.error("handleTinyMCEmath unable to compile LaTeX using " + "mimetex, error = " + str(e))
             raise
         server_filename = previewDir.joinpath(preview_image_filename)
         log.debug(
             "handleTinyMCEmath copying math image from '"
             + tempFileName
             + "' to '"
             + server_filename.abspath().encode("utf-8")
             + "'."
         )
         shutil.copyfile(tempFileName, server_filename.abspath().encode("utf-8"))
         Path(tempFileName).remove()
Beispiel #8
0
    def handleExport(self, client, exportType, filename, print_callback=''):
        """
        Called by js. 
        Exports the current package to one of the above formats
        'exportType' can be one of 'singlePage' 'webSite' 'zipFile' 'ipod'
                     'textFile' or 'scorm'
        'filename' is a file for scorm pages, and a directory for websites
        """ 
        webDir     = Path(self.config.webDir)
        stylesDir  = webDir.joinpath('style', self.package.style)

        exportDir  = Path(filename).dirname()
        if exportDir and not exportDir.exists():
            client.alert(_(u'Cannot access directory named ') +
                         unicode(exportDir) +
                         _(u'. Please use ASCII names.'))
            return

        """ 
        adding the print feature in using the same export functionality:
        """
        if exportType == 'singlePage' or exportType == 'printSinglePage':
            printit = 0
            if exportType == 'printSinglePage':
                printit = 1
            exported_dir = self.exportSinglePage(client, filename, webDir, \
                                                 stylesDir, printit)
            # the above will return None if the desired exported directory
            # already exists (printing always goes to a new temp dir, though):
            if printit == 1 and not exported_dir is None:
                web_printdir = self.get_printdir_relative2web(exported_dir)
                # now that this has ben exported, go ahead and trigger 
                # the requested printing callback:
                client.call(print_callback, filename, exported_dir, \
                            web_printdir)

        elif exportType == 'webSite':
            self.exportWebSite(client, filename, stylesDir)
            
        elif exportType == 'zipFile':
            filename = self.b4save(client, filename, '.zip', _(u'EXPORT FAILED!'))
            self.exportWebZip(client, filename, stylesDir)
        elif exportType == 'textFile':
            self.exportText(client, filename)
        elif exportType == 'ipod':
            self.exportIpod(client, filename)
        elif exportType == "scorm":
            filename = self.b4save(client, filename, '.zip', _(u'EXPORT FAILED!'))
            self.exportScorm(client, filename, stylesDir, "scorm1.2")
        elif exportType == "scorm2004":
            filename = self.b4save(client, filename, '.zip', _(u'EXPORT FAILED!'))
            self.exportScorm(client, filename, stylesDir, "scorm2004")
        elif exportType == "commoncartridge":
            filename = self.b4save(client, filename, '.zip', _(u'EXPORT FAILED!'))
            self.exportScorm(client, filename, stylesDir, "commoncartridge")
        else:
            filename = self.b4save(client, filename, '.zip', _(u'EXPORT FAILED!'))
            self.exportIMS(client, filename, stylesDir)
    def copyFiles(self, package):
        """
        Copy all the files used by the website.
        """
        # Copy the style files to the output dir
        # But not nav.css
        if os.path.isdir(self.stylesDir):
            styleFiles = [self.stylesDir / '..' / 'popup_bg.gif']
            styleFiles += self.stylesDir.files("*.*")
            if "nav.css" in styleFiles:
                styleFiles.remove("nav.css")
            self.stylesDir.copylist(styleFiles, self.outputDir)

        # copy the package's resource files
        package.resourceDir.copyfiles(self.outputDir)

        listCSSFiles = getFilesCSSToMinify('singlepage', self.stylesDir)
        exportMinFileCSS(listCSSFiles, self.outputDir)

        # copy script files.
        my_style = G.application.config.styleStore.getStyle(package.style)

        # jQuery
        if my_style.hasValidConfig:
            if my_style.get_jquery() == True:
                jsFile = (self.scriptsDir / 'exe_jquery.js')
                jsFile.copyfile(self.outputDir / 'exe_jquery.js')
        else:
            jsFile = (self.scriptsDir / 'exe_jquery.js')
            jsFile.copyfile(self.outputDir / 'exe_jquery.js')

        dT = common.getExportDocType()
        if dT == "HTML5":
            jsFile = (self.scriptsDir / 'exe_html5.js')
            jsFile.copyfile(self.outputDir / 'exe_html5.js')

        # Minify common.js file
        listFiles = getFilesJSToMinify('singlepage', self.scriptsDir)
        exportMinFileJS(listFiles, self.outputDir)

        # Incluide eXe's icon if the Style doesn't have one
        themePath = Path(G.application.config.stylesDir / package.style)
        themeFavicon = themePath.joinpath("favicon.ico")
        if not themeFavicon.exists():
            faviconFile = (self.imagesDir / 'favicon.ico')
            faviconFile.copyfile(self.outputDir / 'favicon.ico')

        #JR Metemos los reproductores necesarios
        self.compruebaReproductores(self.page.node)

        if package.license == "license GFDL":
            # include a copy of the GNU Free Documentation Licence
            ext = 'html'
            if G.application.config.cutFileName == "1":
                ext = 'htm'
            (self.templatesDir / 'fdl' + '.' +
             ext).copyfile(self.outputDir / 'fdl' + '.' + ext)
Beispiel #10
0
 def handleTinyMCEimageChoice(self, client, tinyMCEwin, tinyMCEwin_name, \
                          tinyMCEfield, local_filename, preview_filename):
     """
     Once an image is selected in the file browser that is spawned by the 
     TinyMCE image dialog, copy this file (which is local to the user's 
     machine) into the server space, under a preview directory 
     (after checking if this exists, and creating it if necessary).
     Note that this IS a "cheat", in violation of the client-server 
     separation, but can be done since we know that the eXe server is 
     actually sitting on the client host.
     """
     server_filename = ""
     callback_errors = ""
     errors = 0
     webDir     = Path(self.config.webDir)
     previewDir  = webDir.joinpath('previews')
     if not previewDir.exists():
         log.debug("image previews directory does not yet exist; " \
                 + "creating as %s " % previewDir)
         previewDir.makedirs()
     elif not previewDir.isdir():
         client.alert( \
             _(u'Preview directory %s is a file, cannot replace it') \
             % previewDir)
         log.error("Couldn't preview tinyMCE-chosen image: "+
                   "Preview dir %s is a file, cannot replace it" \
                   % previewDir)
         callback_errors =  "Preview dir is a file, cannot replace"
         errors += 1
     if errors == 0:
         localImagePath = Path(local_filename)
         if not localImagePath.exists() or not localImagePath.isfile():
             client.alert( \
                  _(u'Image file %s is not found, cannot preview it') \
                  % localImagePath)
             log.error("Couldn't find tinyMCE-chosen image: %s" \
                     % localImagePath)
             callback_errors = "Image file %s not found, cannot preview" \
                     % localImagePath
             errors += 1
     try:
         server_filename = previewDir.joinpath(preview_filename);
         log.debug("handleTinyMCEimageChoice copying image from \'"\
                 + local_filename + "\' to \'" \
                 + server_filename.abspath().encode('utf-8') + "\'.");
         shutil.copyfile(local_filename, \
                 server_filename.abspath().encode('utf-8'));
     except Exception, e:
         client.alert(_('SAVE FAILED!\n%s' % str(e)))
         log.error("handleTinyMCEimageChoice unable to copy local image "\
                 +"file to server prevew, error = " + str(e))
         raise
Beispiel #11
0
 def handleExport(self, client, exportType, filename, print_callback=""):
     """
     Called by js. 
     Exports the current package to one of the above formats
     'exportType' can be one of 'singlePage' 'webSite' 'zipFile' 'ipod'
                  'textFile' or 'scorm'
     'filename' is a file for scorm pages, and a directory for websites
     """
     webDir = Path(self.config.webDir)
     stylesDir = webDir.joinpath("style", self.package.style)
     exportDir = Path(filename).dirname()
     if exportDir and not exportDir.exists():
         client.alert(_(u"Cannot access directory named ") + unicode(exportDir) + _(u". Please use ASCII names."))
         return
     """ 
     adding the print feature in using the same export functionality:
     """
     if exportType == "singlePage" or exportType == "printSinglePage":
         printit = 0
         if exportType == "printSinglePage":
             printit = 1
         exported_dir = self.exportSinglePage(client, filename, webDir, stylesDir, printit)
         if printit == 1 and not exported_dir is None:
             web_printdir = self.get_printdir_relative2web(exported_dir)
             client.call(print_callback, filename, exported_dir, web_printdir)
     elif exportType == "webSite":
         self.exportWebSite(client, filename, stylesDir)
     elif exportType == "zipFile":
         filename = self.b4save(client, filename, ".zip", _(u"EXPORT FAILED!"))
         self.exportWebZip(client, filename, stylesDir)
     elif exportType == "textFile":
         self.exportText(client, filename)
     elif exportType == "ipod":
         self.exportIpod(client, filename)
     elif exportType == "scorm":
         filename = self.b4save(client, filename, ".zip", _(u"EXPORT FAILED!"))
         self.exportScorm(client, filename, stylesDir, "scorm1.2")
     elif exportType == "scorm2004":
         filename = self.b4save(client, filename, ".zip", _(u"EXPORT FAILED!"))
         self.exportScorm(client, filename, stylesDir, "scorm2004")
     elif exportType == "commoncartridge":
         filename = self.b4save(client, filename, ".zip", _(u"EXPORT FAILED!"))
         self.exportScorm(client, filename, stylesDir, "commoncartridge")
     else:
         filename = self.b4save(client, filename, ".zip", _(u"EXPORT FAILED!"))
         self.exportIMS(client, filename, stylesDir)
Beispiel #12
0
 def _process(self, request):
     """
     Delegates processing of args to blocks
     """  
     self.parent.process(request)
     if ("action" in request.args and 
         request.args["action"][0] == u"saveChange"):
         log.debug(u"process savachange:::::")
         self.package.save()
         log.debug(u"package name: " + self.package.name)
     for block in self.blocks:
         block.process(request)
     webDir     = Path(G.application.config.webDir) 
     previewDir  = webDir.joinpath('previews')
     for root, dirs, files in os.walk(previewDir, topdown=False): 
         for name in files: 
             os.remove(os.path.join(root, name))
     log.debug(u"After authoringPage process" + repr(request.args))
Beispiel #13
0
 def handleExport(self, client, exportType, filename, print_callback=''):
     """
     Called by js. 
     Exports the current package to one of the above formats
     'exportType' can be one of 'singlePage' 'webSite' 'zipFile'
                  'textFile' or 'scorm'
     'filename' is a file for scorm pages, and a directory for websites
     """ 
     webDir     = Path(self.config.webDir)
     stylesDir  = webDir.joinpath('style', self.package.style)
     exportDir  = Path(filename).dirname()
     if exportDir and not exportDir.exists():
         client.alert(_(u'Cannot access directory named ') +
                      unicode(exportDir) +
                      _(u'. Please use ASCII names.'))
         return
     """ if exportType == 'singlePage':
     r3m0: adding the print feature in using the same export functionality:
     """
     if exportType == 'singlePage' or exportType == 'printSinglePage':
         printit = 0
         if exportType == 'printSinglePage':
             printit = 1
         exported_dir = self.exportSinglePage(client, filename, webDir, stylesDir, printit)
         if printit == 1:
             client.call(print_callback, filename, exported_dir)
     elif exportType == 'webSite':
         self.exportWebSite(client, filename, stylesDir)
     elif exportType == 'zipFile':
         filename = self.b4save(client, filename, '.zip', _(u'EXPORT FAILED!'))
         self.exportWebZip(client, filename, stylesDir)
     elif exportType == 'textFile':
         self.exportText(client, filename)
     elif exportType == "scorm":
         filename = self.b4save(client, filename, '.zip', _(u'EXPORT FAILED!'))
         self.exportScorm(client, filename, stylesDir, "scorm1.2")
     elif exportType == "scorm2004":
         filename = self.b4save(client, filename, '.zip', _(u'EXPORT FAILED!'))
         self.exportScorm(client, filename, stylesDir, "scorm2004")
     else:
         filename = self.b4save(client, filename, '.zip', _(u'EXPORT FAILED!'))
         self.exportIMS(client, filename, stylesDir)
Beispiel #14
0
    def __renderHeader(self):
		#TinyMCE lang (user preference)
        myPreferencesPage = self.webServer.preferences
        
        """Generates the header for AuthoringPage"""
        html  = common.docType()
        #################################################################################
        #################################################################################
        
        html += u'<html xmlns="http://www.w3.org/1999/xhtml" lang="'+myPreferencesPage.getSelectedLanguage()+'">\n'
        html += u'<head>\n'
        html += u"<link rel=\"stylesheet\" type=\"text/css\" href=\"/css/exe.css\" />"
        
        # Use the Style's base.css file if it exists
        themePath = Path(G.application.config.stylesDir/self.package.style)
        themeBaseCSS = themePath.joinpath("base.css")
        if themeBaseCSS.exists():
            html += u"<link rel=\"stylesheet\" type=\"text/css\" href=\"/style/%s/base.css\" />" % self.package.style
        else:
            html += u"<link rel=\"stylesheet\" type=\"text/css\" href=\"/style/base.css\" />"
            
        html += u"<link rel=\"stylesheet\" type=\"text/css\" href=\"/css/exe_wikipedia.css\" />"
        html += u"<link rel=\"stylesheet\" type=\"text/css\" href=\"/style/%s/content.css\" />" % self.package.style
        if G.application.config.assumeMediaPlugins: 
            html += u"<script type=\"text/javascript\">var exe_assume_media_plugins = true;</script>\n"
        #JR: anado una variable con el estilo
        estilo = u'/style/%s/content.css' % self.package.style
        html += common.getJavaScriptStrings()
        html += u"<script type=\"text/javascript\">var exe_style = '%s';</script>\n" % estilo
        html += u"<script type=\"text/javascript\">var exe_package_name='"+self.package.name+"';</script>\n"			
        html += u'<script type="text/javascript" src="../jsui/native.history.js"></script>\n'
        html += u'<script type="text/javascript" src="/scripts/authoring.js"></script>\n'
        html += u'<script type="text/javascript" src="/scripts/exe_jquery.js"></script>\n'
        html += u'<script type="text/javascript" src="/scripts/exe_lightbox.js"></script>\n'
        html += u'<script type="text/javascript" src="/scripts/common.js"></script>\n'
        html += '<script type="text/javascript">document.write(unescape("%3Cscript src=\'" + eXeLearning_settings.wysiwyg_path + "\' type=\'text/javascript\'%3E%3C/script%3E"));</script>';
        html += '<script type="text/javascript">document.write(unescape("%3Cscript src=\'" + eXeLearning_settings.wysiwyg_settings_path + "\' type=\'text/javascript\'%3E%3C/script%3E"));</script>';
        html += u'<title>"+_("eXe : elearning XHTML editor")+"</title>\n'
        html += u'<meta http-equiv="content-type" content="text/html; '
        html += u' charset=UTF-8" />\n'
        html += u'</head>\n'
        return html
Beispiel #15
0
    def _process(self, request):
        """
        Delegates processing of args to blocks
        """
        # Still need to call parent (mainpage.py) process
        # because the idevice pane needs to know that new idevices have been
        # added/edited..
        self.parent.process(request)
        for block in self.blocks:
            block.process(request)
        # now that each block and corresponding elements have been processed,
        # it's finally safe to remove any images/etc which made it into
        # tinyMCE's previews directory, as they have now had their
        # corresponding resources created:
        webDir = Path(G.application.tempWebDir)
        previewDir = webDir.joinpath('previews')
        for root, dirs, files in os.walk(previewDir, topdown=False):
            for name in files:
                if sys.platform[:3] == "win":
                    for i in range(3):
                        try:
                            os.remove(os.path.join(root, name))
                            break
                        except exceptions.WindowsError:
                            time.sleep(0.3)
                else:
                    os.remove(os.path.join(root, name))
        topNode = self.package.currentNode
        if "action" in request.args:
            if request.args["action"][0] == u"changeNode":
                topNode = self.package.findNode(request.args["object"][0])
            elif "currentNode" in request.args:
                topNode = self.package.findNode(request.args["currentNode"][0])
        elif "currentNode" in request.args:
            topNode = self.package.findNode(request.args["currentNode"][0])

        log.debug(u"After authoringPage process" + repr(request.args))
        return topNode
    def _process(self, request):
        """
        Delegates processing of args to blocks
        """  
        # Still need to call parent (mainpage.py) process
        # because the idevice pane needs to know that new idevices have been
        # added/edited..
        self.parent.process(request)
        for block in self.blocks:
            block.process(request)
        # now that each block and corresponding elements have been processed,
        # it's finally safe to remove any images/etc which made it into 
        # tinyMCE's previews directory, as they have now had their 
        # corresponding resources created:
        webDir     = Path(G.application.tempWebDir) 
        previewDir  = webDir.joinpath('previews')
        for root, dirs, files in os.walk(previewDir, topdown=False): 
            for name in files:
                if sys.platform[:3] == "win":
                    for i in range(3):
                        try:
                            os.remove(os.path.join(root, name))
                            break
                        except exceptions.WindowsError:
                            time.sleep(0.3)
                else:
                    os.remove(os.path.join(root, name))
        topNode = self.package.currentNode
        if "action" in request.args:
            if request.args["action"][0] == u"changeNode":
                topNode = self.package.findNode(request.args["object"][0])
            elif "currentNode" in request.args:
                topNode = self.package.findNode(request.args["currentNode"][0])
        elif "currentNode" in request.args:
            topNode = self.package.findNode(request.args["currentNode"][0])

        log.debug(u"After authoringPage process" + repr(request.args))
        return topNode
Beispiel #17
0
    def copyFiles(self, package, outputDir):
        """
        Copy all the files used by the website.
        """

        if os.path.isdir(self.stylesDir):
            # Copy the style files to the output dir
            styleFiles = [self.stylesDir/'..'/'popup_bg.gif']
            styleFiles += self.stylesDir.files("*.*")
            self.stylesDir.copylist(styleFiles, outputDir)

        # copy the package's resource files
        for resourceFile in package.resourceDir.walkfiles():
            file = package.resourceDir.relpathto(resourceFile)

            if ("/" in file):
                Dir = Path(outputDir/file[:file.rindex("/")])

                if not Dir.exists():
                    Dir.makedirs()

                resourceFile.copy(outputDir/Dir)
            else:
                resourceFile.copy(outputDir)

        listCSSFiles=getFilesCSSToMinify('website', self.stylesDir)
        exportMinFileCSS(listCSSFiles, outputDir)

        # copy script files.
        my_style = G.application.config.styleStore.getStyle(package.style)
        # jQuery
        listFiles=[]
        listOutFiles=[]
        if my_style.hasValidConfig:
            if my_style.get_jquery() == True:
                jsFile = (self.scriptsDir/'exe_jquery.js')
                jsFile.copyfile(outputDir/'exe_jquery.js')
        else:
            listFiles+=[self.scriptsDir/'exe_jquery.js']
            listOutFiles+=[outputDir/'exe_jquery.js']

        # Minify common.js file
        listFiles=getFilesJSToMinify('website', self.scriptsDir)
        exportMinFileJS(listFiles, outputDir)

        # Create lang file
        langFile = open(outputDir + '/common_i18n.js', "w")
        langFile.write(common.getJavaScriptStrings(False))
        langFile.close()
        #dT = common.getExportDocType()
        dT=common.getExportDocType();
        if dT == "HTML5":
            jsFile = (self.scriptsDir/'exe_html5.js')
            jsFile.copyfile(outputDir/'exe_html5.js')

        # Incluide eXe's icon if the Style doesn't have one
        themePath = Path(G.application.config.stylesDir/package.style)
        themeFavicon = themePath.joinpath("favicon.ico")
        if not themeFavicon.exists():
            faviconFile = (self.imagesDir/'favicon.ico')
            faviconFile.copyfile(outputDir/'favicon.ico')

        # copy players for media idevices.
        hasFlowplayer     = False
        hasMagnifier      = False
        hasXspfplayer     = False
        hasGallery        = False
        hasFX             = False
        hasSH             = False
        hasGames          = False
        hasElpLink        = False
        hasWikipedia      = False
        isBreak           = False
        hasInstructions   = False
        hasMediaelement   = False
        hasTooltips       = False
        hasABCMusic       = False
        listIdevicesFiles = []

        for page in self.pages:
            if isBreak:
                break
            for idevice in page.node.idevices:
                if (hasFlowplayer and hasMagnifier and hasXspfplayer and hasGallery and hasFX and hasSH and hasGames and hasElpLink and hasWikipedia and hasInstructions and hasMediaelement and hasTooltips and hasABCMusic):
                    isBreak = True
                    break
                if not hasFlowplayer:
                    if 'flowPlayer.swf' in idevice.systemResources:
                        hasFlowplayer = True
                if not hasMagnifier:
                    if 'mojomagnify.js' in idevice.systemResources:
                        hasMagnifier = True
                if not hasXspfplayer:
                    if 'xspf_player.swf' in idevice.systemResources:
                        hasXspfplayer = True
                if not hasGallery:
                    hasGallery = common.ideviceHasGallery(idevice)
                if not hasFX:
                    hasFX = common.ideviceHasFX(idevice)
                if not hasSH:
                    hasSH = common.ideviceHasSH(idevice)
                if not hasGames:
                    hasGames = common.ideviceHasGames(idevice)
                if not hasElpLink:
                    hasElpLink = common.ideviceHasElpLink(idevice,package)
                if not hasWikipedia:
                    if 'WikipediaIdevice' == idevice.klass:
                        hasWikipedia = True
                if not hasInstructions:
                    if 'TrueFalseIdevice' == idevice.klass or 'MultichoiceIdevice' == idevice.klass or 'VerdaderofalsofpdIdevice' == idevice.klass or 'EleccionmultiplefpdIdevice' == idevice.klass:
                        hasInstructions = True
                if not hasMediaelement:
                    hasMediaelement = common.ideviceHasMediaelement(idevice)
                if not hasTooltips:
                    hasTooltips = common.ideviceHasTooltips(idevice)
                if not hasABCMusic:
                    hasABCMusic = common.ideviceHasABCMusic(idevice)
                if hasattr(idevice, "_iDeviceDir"):
                    listIdevicesFiles.append((Path(idevice._iDeviceDir)/'export'))

            common.exportJavaScriptIdevicesFiles(page.node.idevices, outputDir);

        if hasFlowplayer:
            videofile = (self.templatesDir/'flowPlayer.swf')
            videofile.copyfile(outputDir/'flowPlayer.swf')
            controlsfile = (self.templatesDir/'flowplayer.controls.swf')
            controlsfile.copyfile(outputDir/'flowplayer.controls.swf')
        if hasMagnifier:
            videofile = (self.templatesDir/'mojomagnify.js')
            videofile.copyfile(outputDir/'mojomagnify.js')
        if hasXspfplayer:
            videofile = (self.templatesDir/'xspf_player.swf')
            videofile.copyfile(outputDir/'xspf_player.swf')
        if hasGallery:
            exeLightbox = (self.scriptsDir/'exe_lightbox')
            exeLightbox.copyfiles(outputDir)
        if hasFX:
            exeEffects = (self.scriptsDir/'exe_effects')
            exeEffects.copyfiles(outputDir)
        if hasSH:
            exeSH = (self.scriptsDir/'exe_highlighter')
            exeSH.copyfiles(outputDir)
        if hasGames:
            exeGames = (self.scriptsDir/'exe_games')
            exeGames.copyfiles(outputDir)
            # Add game js string to common_i18n
            langGameFile = open(outputDir + '/common_i18n.js', "a")
            langGameFile.write(common.getGamesJavaScriptStrings(False))
            langGameFile.close()
        if hasElpLink or package.get_exportElp():
            # Export the elp file
            currentPackagePath = Path(package.filename)
            currentPackagePath.copyfile(outputDir/package.name+'.elp')
        if hasABCMusic:
            pluginScripts = (self.scriptsDir/'tinymce_4/js/tinymce/plugins/abcmusic/export')
            pluginScripts.copyfiles(outputDir)
        if hasWikipedia:
            wikipediaCSS = (self.cssDir/'exe_wikipedia.css')
            wikipediaCSS.copyfile(outputDir/'exe_wikipedia.css')
        if hasInstructions:
            common.copyFileIfNotInStyle('panel-amusements.png', self, outputDir)
            common.copyFileIfNotInStyle('stock-stop.png', self, outputDir)
        if hasMediaelement:
            mediaelement = (self.scriptsDir/'mediaelement')
            mediaelement.copyfiles(outputDir)
            dT = common.getExportDocType()
            if dT != "HTML5":
                jsFile = (self.scriptsDir/'exe_html5.js')
                jsFile.copyfile(outputDir/'exe_html5.js')
        if hasTooltips:
            exe_tooltips = (self.scriptsDir/'exe_tooltips')
            exe_tooltips.copyfiles(outputDir)

        if hasattr(package, 'exportSource') and package.exportSource:
            (G.application.config.webDir/'templates'/'content.xsd').copyfile(outputDir/'content.xsd')
            (outputDir/'content.data').write_bytes(encodeObject(package))
            (outputDir/'contentv3.xml').write_bytes(encodeObjectToXML(package))
        ext = 'html'
        if G.application.config.cutFileName == "1":
            ext = 'htm'
        if package.license == "license GFDL":
            # include a copy of the GNU Free Documentation Licence
            (self.templatesDir/'fdl' + '.' + ext).copyfile(outputDir/'fdl' + '.' + ext)
Beispiel #18
0
    def __renderHeader(self):
        #TinyMCE lang (user preference)
        myPreferencesPage = self.webServer.preferences
        """Generates the header for AuthoringPage"""
        html = common.docType()
        #################################################################################
        #################################################################################

        html += u'<html xmlns="http://www.w3.org/1999/xhtml" lang="' + myPreferencesPage.getSelectedLanguage(
        ) + '">\n'
        html += u'<head>\n'
        html += u"<link rel=\"stylesheet\" type=\"text/css\" href=\"/css/exe.css\" />"

        # Use the Style's base.css file if it exists
        themePath = Path(G.application.config.stylesDir / self.package.style)
        themeBaseCSS = themePath.joinpath("base.css")
        if themeBaseCSS.exists():
            html += u"<link rel=\"stylesheet\" type=\"text/css\" href=\"/style/%s/base.css\" />" % self.package.style
        else:
            html += u"<link rel=\"stylesheet\" type=\"text/css\" href=\"/style/base.css\" />"

        html += u"<link rel=\"stylesheet\" type=\"text/css\" href=\"/css/exe_wikipedia.css\" />"
        html += u"<link rel=\"stylesheet\" type=\"text/css\" href=\"/scripts/exe_effects/exe_effects.css\" />"
        html += u"<link rel=\"stylesheet\" type=\"text/css\" href=\"/scripts/exe_highlighter/exe_highlighter.css\" />"
        html += u"<link rel=\"stylesheet\" type=\"text/css\" href=\"/scripts/exe_games/exe_games.css\" />"
        html += u"<link rel=\"stylesheet\" type=\"text/css\" href=\"/scripts/tinymce_4/js/tinymce/plugins/abcmusic/export/exe_abcmusic.css\" />"  #93 (to do)
        html += u"<link rel=\"stylesheet\" type=\"text/css\" href=\"/style/%s/content.css\" />" % self.package.style
        if G.application.config.assumeMediaPlugins:
            html += u"<script type=\"text/javascript\">var exe_assume_media_plugins = true;</script>\n"
        #JR: anado una variable con el estilo
        estilo = u'/style/%s/content.css' % self.package.style
        html += common.getJavaScriptStrings()
        # The games require additional strings
        html += common.getGamesJavaScriptStrings()
        html += u"<script type=\"text/javascript\">"
        html += u"var exe_style = '%s';top.exe_style = exe_style;" % estilo
        # editorpane.py uses exe_style_dirname to auto-select the current style (just a provisional solution)
        html += u"var exe_style_dirname = '%s'; top.exe_style_dirname = exe_style_dirname;" % self.package.style
        html += u"var exe_package_name='" + self.package.name + "';"
        html += 'var exe_export_format="' + common.getExportDocType(
        ) + '".toLowerCase();'
        html += 'var exe_editor_mode="' + myPreferencesPage.getEditorMode(
        ) + '";'
        html += 'var exe_editor_version="' + myPreferencesPage.getEditorVersion(
        ) + '";'
        html += '</script>\n'
        html += u'<script type="text/javascript" src="../jsui/native.history.js"></script>\n'
        htmlLang = G.application.config.locale
        if self.package.dublinCore.language != "":
            htmlLang = self.package.dublinCore.language
        for subDir in G.application.config.localeDir.dirs():
            if (subDir / 'LC_MESSAGES' / 'exe.mo').exists():
                if str(
                        subDir.basename()
                ) == htmlLang and htmlLang != myPreferencesPage.getSelectedLanguage(
                ):
                    html += u'<script type="text/javascript" src="../jsui/i18n/' + htmlLang + '.js"></script>\n'
                    html += u'<script type="text/javascript">var exe_elp_lang="' + htmlLang + '";</script>\n'
        html += u'<script type="text/javascript" src="/scripts/authoring.js"></script>\n'
        html += u'<script type="text/javascript" src="/scripts/exe_jquery.js"></script>\n'
        html += u'<script type="text/javascript" src="/scripts/exe_lightbox/exe_lightbox.js"></script>\n'
        html += u'<script type="text/javascript" src="/scripts/exe_effects/exe_effects.js"></script>\n'
        html += u'<script type="text/javascript" src="/scripts/exe_highlighter/exe_highlighter.js"></script>\n'
        html += u'<script type="text/javascript" src="/scripts/exe_games/exe_games.js"></script>\n'
        html += u'<script type="text/javascript" src="/scripts/tinymce_4/js/tinymce/plugins/abcmusic/export/exe_abcmusic.js"></script>\n'  #93 (to do)
        html += u'<script type="text/javascript" src="/scripts/common.js"></script>\n'
        html += '<script type="text/javascript">document.write(unescape("%3Cscript src=\'" + eXeLearning_settings.wysiwyg_path + "\' type=\'text/javascript\'%3E%3C/script%3E"));</script>'
        html += '<script type="text/javascript">document.write(unescape("%3Cscript src=\'" + eXeLearning_settings.wysiwyg_settings_path + "\' type=\'text/javascript\'%3E%3C/script%3E"));</script>'
        html += common.printJavaScriptIdevicesScripts('edition', self)
        html += u'<title>"+_("eXe : elearning XHTML editor")+"</title>\n'
        html += u'<meta http-equiv="content-type" content="text/html; '
        html += u' charset=UTF-8" />\n'
        style = G.application.config.styleStore.getStyle(self.package.style)
        if style.hasValidConfig():
            html += style.get_edition_extra_head()
        html += common.getExtraHeadContent(self.package)
        html += u'</head>\n'
        return html
    def handleExport(self, client, exportType, filename, print_callback=''):
        """
        Called by js. 
        Exports the current package to one of the above formats
        'exportType' can be one of 'singlePage' 'webSite' 'zipFile' 'ipod'
                     'textFile' or 'scorm'
        'filename' is a file for scorm pages, and a directory for websites
        """
        webDir = Path(self.config.webDir)
        stylesDir = webDir.joinpath('style', self.package.style)

        exportDir = Path(filename).dirname()
        if exportDir and not exportDir.exists():
            client.alert(
                _(u'Cannot access directory named ') + unicode(exportDir) +
                _(u'. Please use ASCII names.'))
            return
        """ 
        adding the print feature in using the same export functionality:
        """
        if exportType == 'singlePage' or exportType == 'printSinglePage':
            printit = 0
            if exportType == 'printSinglePage':
                printit = 1
            exported_dir = self.exportSinglePage(client, filename, webDir, \
                                                 stylesDir, printit)
            # the above will return None if the desired exported directory
            # already exists (printing always goes to a new temp dir, though):
            if printit == 1 and not exported_dir is None:
                web_printdir = self.get_printdir_relative2web(exported_dir)
                # now that this has ben exported, go ahead and trigger
                # the requested printing callback:
                client.call(print_callback, filename, exported_dir, \
                            web_printdir)

        elif exportType == 'webSite':
            self.exportWebSite(client, filename, stylesDir)

        elif exportType == 'zipFile':
            filename = self.b4save(client, filename, '.zip',
                                   _(u'EXPORT FAILED!'))
            self.exportWebZip(client, filename, stylesDir)
        elif exportType == 'textFile':
            self.exportText(client, filename)
        elif exportType == 'ipod':
            self.exportIpod(client, filename)
        elif exportType == "scorm":
            filename = self.b4save(client, filename, '.zip',
                                   _(u'EXPORT FAILED!'))
            self.exportScorm(client, filename, stylesDir, "scorm1.2")
        elif exportType == "scorm2004":
            filename = self.b4save(client, filename, '.zip',
                                   _(u'EXPORT FAILED!'))
            self.exportScorm(client, filename, stylesDir, "scorm2004")
        elif exportType == "commoncartridge":
            filename = self.b4save(client, filename, '.zip',
                                   _(u'EXPORT FAILED!'))
            self.exportScorm(client, filename, stylesDir, "commoncartridge")
        else:
            filename = self.b4save(client, filename, '.zip',
                                   _(u'EXPORT FAILED!'))
            self.exportIMS(client, filename, stylesDir)
    def handleTinyMCEimageChoice(self, client, tinyMCEwin, tinyMCEwin_name, \
                             tinyMCEfield, local_filename, preview_filename):
        """
        Once an image is selected in the file browser that is spawned by the 
        TinyMCE image dialog, copy this file (which is local to the user's 
        machine) into the server space, under a preview directory 
        (after checking if this exists, and creating it if necessary).
        Note that this IS a "cheat", in violation of the client-server 
        separation, but can be done since we know that the eXe server is 
        actually sitting on the client host.
        """
        server_filename = ""
        callback_errors = ""
        errors = 0

        log.debug('handleTinyMCEimageChoice: image local = ' + local_filename +
                  ', base=' + os.path.basename(local_filename))

        webDir = Path(G.application.tempWebDir)
        previewDir = webDir.joinpath('previews')

        if not previewDir.exists():
            log.debug("image previews directory does not yet exist; " \
                    + "creating as %s " % previewDir)
            previewDir.makedirs()
        elif not previewDir.isdir():
            client.alert( \
                _(u'Preview directory %s is a file, cannot replace it') \
                % previewDir)
            log.error("Couldn't preview tinyMCE-chosen image: "+
                      "Preview dir %s is a file, cannot replace it" \
                      % previewDir)
            callback_errors = "Preview dir is a file, cannot replace"
            errors += 1

        if errors == 0:
            log.debug('handleTinyMCEimageChoice: originally, local_filename=' +
                      local_filename)
            local_filename = unicode(local_filename, 'utf-8')
            log.debug('handleTinyMCEimageChoice: in unicode, local_filename=' +
                      local_filename)

            localImagePath = Path(local_filename)
            log.debug(
                'handleTinyMCEimageChoice: after Path, localImagePath= ' +
                localImagePath)
            if not localImagePath.exists() or not localImagePath.isfile():
                client.alert( \
                     _(u'Local file %s is not found, cannot preview it') \
                     % localImagePath)
                log.error("Couldn't find tinyMCE-chosen image: %s" \
                        % localImagePath)
                callback_errors = "Image file %s not found, cannot preview" \
                        % localImagePath
                errors += 1

        try:
            # joinpath needs its join arguments to already be in Unicode:
            #preview_filename = toUnicode(preview_filename);
            # but that's okay, cuz preview_filename is now URI safe, right?
            log.debug('URIencoded preview filename=' + preview_filename)

            server_filename = previewDir.joinpath(preview_filename)
            log.debug("handleTinyMCEimageChoice copying image from \'"\
                    + local_filename + "\' to \'" \
                    + server_filename.abspath() + "\'.")
            shutil.copyfile(local_filename, \
                    server_filename.abspath())

            # new optional description file to provide the
            # actual base filename, such that once it is later processed
            # copied into the resources directory, it can be done with
            # only the basename.   Otherwise the resource filenames
            # are too long for some users, preventing them from making
            # backup CDs of the content, for example.
            #
            # Remember that the full path of the
            # file is only used here as an easy way to keep the names
            # unique WITHOUT requiring a roundtrip call from the Javascript
            # to this server, and back again, a process which does not
            # seem to work with tinyMCE in the mix.  BUT, once tinyMCE's
            # part is done, and this image processed, it can be returned
            # to just its basename, since the resource parts have their
            # own unique-ification mechanisms already in place.

            descrip_file_path = Path(server_filename + ".exe_info")
            log.debug("handleTinyMCEimageChoice creating preview " \
                    + "description file \'" \
                    + descrip_file_path.abspath() + "\'.")
            descrip_file = open(descrip_file_path, 'wb')

            # safety measures against TinyMCE, otherwise it will
            # later take ampersands and entity-escape them into '&amp;',
            # and filenames with hash signs will not be found, etc.:
            unspaced_filename = local_filename.replace(' ', '_')
            unhashed_filename = unspaced_filename.replace('#', '_num_')
            unamped_local_filename = unhashed_filename.replace('&', '_and_')
            log.debug("and setting new file basename as: " +
                      unamped_local_filename)
            my_basename = os.path.basename(unamped_local_filename)
            descrip_file.write((u"basename=" + my_basename).encode('utf-8'))

            descrip_file.flush()
            descrip_file.close()

        except Exception, e:
            client.alert(_('SAVE FAILED!\n%s' % str(e)))
            log.error("handleTinyMCEimageChoice unable to copy local image "\
                    +"file to server prevew, error = " + str(e))
            raise
Beispiel #21
0
 def convertToFreeText(self):
     """
     Actually do the Converting of 
           MathsIdevice -> FreeTextIdevice,
     now that FreeText can hold embeddded images.
     """
     new_content = ""
     imageResource_exists = False
     if not self.content.gifResource is None:
         if os.path.exists(self.content.gifResource.path) and \
         os.path.isfile(self.content.gifResource.path): 
             imageResource_exists = True
         else:
             log.warn("Couldn't find Maths image when upgrading "\
                     + self.content.gifResource.storageName)
     if imageResource_exists:
         new_content += "<img src=\"resources/" \
                 + self.content.gifResource.storageName + "\" " 
         math_resource_url="resources/" \
                 + self.content.gifResource.storageName + ".tex\" " 
         new_content += "exe_math_latex=\"" + math_resource_url + "\" "
         new_content += "exe_math_size=\"" + repr(self.content.fontsize) \
                 + "\" "
         new_content += "/> \n"
     elif self.content.gifResource:
         new_content += "<BR>\n[WARNING: missing image: " \
                 + self.content.gifResource.storageName + "]\n"
     replacementIdev = FreeTextIdevice(new_content)
     replacementIdev.content.content_wo_resourcePaths = \
             replacementIdev.content.MassageContentForRenderView( \
                 replacementIdev.content.content_w_resourcePaths)
     self.parentNode.addIdevice(replacementIdev)
     replacementIdev.content.setParentNode()
     if imageResource_exists:
         from exe.engine.galleryidevice  import GalleryImage 
         full_image_path = self.content.gifResource.path
         new_GalleryImage = GalleryImage(replacementIdev.content, \
                 '',  full_image_path, mkThumbnail=False)
         webDir = Path(G.application.tempWebDir)
         source_tex_name = self.content.gifResource.storageName+".tex"
         math_path = webDir.joinpath(source_tex_name)
         math_filename_str = math_path.abspath().encode('utf-8')
         log.debug("convertToFreeText: writing LaTeX source into \'" \
                                     + math_filename_str + "\'.")
         math_file = open(math_filename_str, 'wb')
         math_file.write(self.content.latex)
         math_file.flush()
         math_file.close()
         new_GalleryLatex = GalleryImage(replacementIdev.content, \
                 '', math_filename_str, mkThumbnail=False) 
         new_GalleryLatexResource = new_GalleryLatex._imageResource
         mathsrc_resource_path = new_GalleryLatexResource._storageName
         mathsrc_resource_url = new_GalleryLatex.resourcesUrl \
                 + mathsrc_resource_path
         if (mathsrc_resource_url != math_resource_url): 
             log.warn('The math source was resource-ified differently ' \
                     + 'than expected, to: ' + mathsrc_resource_url \
                     + '; the source will need to be recreated.') 
         else: 
             log.debug('math source was resource-ified properly to: ' \
                     + mathsrc_resource_url)
     while ( self.parentNode.idevices.index(replacementIdev) \
             > ( (self.parentNode.idevices.index(self) + 1))):
         replacementIdev.movePrev()
     self.delete()
Beispiel #22
0
    def handleTinyMCEimageChoice(self, client, tinyMCEwin, tinyMCEwin_name, \
                             tinyMCEfield, local_filename, preview_filename):
        """
        Once an image is selected in the file browser that is spawned by the 
        TinyMCE image dialog, copy this file (which is local to the user's 
        machine) into the server space, under a preview directory 
        (after checking if this exists, and creating it if necessary).
        Note that this IS a "cheat", in violation of the client-server 
        separation, but can be done since we know that the eXe server is 
        actually sitting on the client host.
        """
        server_filename = ""
        callback_errors = ""
        errors = 0

        log.debug('handleTinyMCEimageChoice: image local = ' + local_filename 
                + ', base=' + os.path.basename(local_filename))

        webDir     = Path(G.application.tempWebDir)
        previewDir  = webDir.joinpath('previews')

        if not previewDir.exists():
            log.debug("image previews directory does not yet exist; " \
                    + "creating as %s " % previewDir)
            previewDir.makedirs()
        elif not previewDir.isdir():
            client.alert( \
                _(u'Preview directory %s is a file, cannot replace it') \
                % previewDir)
            log.error("Couldn't preview tinyMCE-chosen image: "+
                      "Preview dir %s is a file, cannot replace it" \
                      % previewDir)
            callback_errors =  "Preview dir is a file, cannot replace"
            errors += 1

        if errors == 0:
            log.debug('handleTinyMCEimageChoice: originally, local_filename='
                    + local_filename)
            local_filename = unicode(local_filename, 'utf-8')
            log.debug('handleTinyMCEimageChoice: in unicode, local_filename='
                    + local_filename)

            localImagePath = Path(local_filename)
            log.debug('handleTinyMCEimageChoice: after Path, localImagePath= '
                    + localImagePath);
            if not localImagePath.exists() or not localImagePath.isfile():
                client.alert( \
                     _(u'Local file %s is not found, cannot preview it') \
                     % localImagePath)
                log.error("Couldn't find tinyMCE-chosen image: %s" \
                        % localImagePath)
                callback_errors = "Image file %s not found, cannot preview" \
                        % localImagePath
                errors += 1

        try:
            # joinpath needs its join arguments to already be in Unicode:
            #preview_filename = toUnicode(preview_filename);
            # but that's okay, cuz preview_filename is now URI safe, right?
            log.debug('URIencoded preview filename=' + preview_filename);

            server_filename = previewDir.joinpath(preview_filename);
            log.debug("handleTinyMCEimageChoice copying image from \'"\
                    + local_filename + "\' to \'" \
                    + server_filename.abspath() + "\'.");
            shutil.copyfile(local_filename, \
                    server_filename.abspath());

            # new optional description file to provide the 
            # actual base filename, such that once it is later processed
            # copied into the resources directory, it can be done with
            # only the basename.   Otherwise the resource filenames
            # are too long for some users, preventing them from making
            # backup CDs of the content, for example.
            # 
            # Remember that the full path of the
            # file is only used here as an easy way to keep the names
            # unique WITHOUT requiring a roundtrip call from the Javascript
            # to this server, and back again, a process which does not
            # seem to work with tinyMCE in the mix.  BUT, once tinyMCE's
            # part is done, and this image processed, it can be returned
            # to just its basename, since the resource parts have their
            # own unique-ification mechanisms already in place.

            descrip_file_path = Path(server_filename+".exe_info")
            log.debug("handleTinyMCEimageChoice creating preview " \
                    + "description file \'" \
                    + descrip_file_path.abspath() + "\'.");
            descrip_file = open(descrip_file_path, 'wb')

            # safety measures against TinyMCE, otherwise it will 
            # later take ampersands and entity-escape them into '&amp;',
            # and filenames with hash signs will not be found, etc.:
            unspaced_filename  = local_filename.replace(' ','_')
            unhashed_filename  = unspaced_filename.replace('#', '_num_')
            unamped_local_filename  = unhashed_filename.replace('&', '_and_')
            log.debug("and setting new file basename as: " 
                    + unamped_local_filename);
            my_basename = os.path.basename(unamped_local_filename)
            descrip_file.write((u"basename="+my_basename).encode('utf-8'))

            descrip_file.flush()
            descrip_file.close()

        except Exception, e:
            client.alert(_('SAVE FAILED!\n%s' % str(e)))
            log.error("handleTinyMCEimageChoice unable to copy local image "\
                    +"file to server prevew, error = " + str(e))
            raise
Beispiel #23
0
    def export(self, package):
        """
        Export SCORM package
        """
        # First do the export to a temporary directory
        outputDir = TempDirPath()

        self.metadataType = package.exportMetadataType

        # copy the package's resource files
        for resourceFile in package.resourceDir.walkfiles():
            file = package.resourceDir.relpathto(resourceFile)

            if ("/" in file):
                Dir = Path(outputDir/file[:file.rindex("/")])

                if not Dir.exists():
                    Dir.makedirs()

                resourceFile.copy(outputDir/Dir)
            else:
                resourceFile.copy(outputDir)

        # copy the package's resource files, only non existant in outputDir
#        outputDirFiles = outputDir.files()
#        for rfile in package.resourceDir.files():
#            if rfile not in outputDirFiles:
#                rfile.copy(outputDir)

        # copy the package's resource files, only indexed in package.resources
#        for md5 in package.resources.values():
#            for resource in md5:
#                resource.path.copy(outputDir)

        # Export the package content
        # Import the Scorm Page class , if the secure mode is off.  If the style has it's own page class
        # use that, else use the default one.
        if self.styleSecureMode=="0":
            if (self.styleDir/"scormpage.py").exists():
                global ScormPage
                module = imp.load_source("ScormPage",self.styleDir/"scormpage.py")
                ScormPage = module.ScormPage


        self.pages = [ ScormPage("index", 1, package.root,
            scormType=self.scormType, metadataType=self.metadataType) ]

        self.generatePages(package.root, 2)
        uniquifyNames(self.pages)

        for page in self.pages:
            page.save(outputDir, self.pages)
            if not self.hasForum:
                for idevice in page.node.idevices:
                    if hasattr(idevice, "isForum"):
                        if idevice.forum.lms.lms == "moodle":
                            self.hasForum = True
                            break

        # Create the manifest file
        manifest = Manifest(self.config, outputDir, package, self.pages, self.scormType, self.metadataType)
        modifiedMetaData = manifest.save("imsmanifest.xml")

        # Create lang file
        langFile = open(outputDir + '/common_i18n.js', "w")
        langFile.write(common.getJavaScriptStrings(False))
        langFile.close()

        if self.hasForum:
            manifest.save("discussionforum.xml")

        # Copy the style files to the output dir

        styleFiles = [self.styleDir/'..'/'popup_bg.gif']
        # And with all the files of the style we avoid problems:
        styleFiles += self.styleDir.files("*.*")
        if self.scormType == "commoncartridge":
            for sf in styleFiles[:]:
                if sf.basename() not in manifest.dependencies:
                    styleFiles.remove(sf)
        self.styleDir.copylist(styleFiles, outputDir)

        listCSSFiles=getFilesCSSToMinify('scorm', self.styleDir)
        exportMinFileCSS(listCSSFiles, outputDir)

        # Copy the scripts

        dT = common.getExportDocType()
        if dT == "HTML5":
            #listFiles+=[self.scriptsDir/'exe_html5.js']
            #listOutFiles+=[outputDir/'exe_html5.js']
            jsFile = (self.scriptsDir/'exe_html5.js')
            jsFile.copyfile(outputDir/'exe_html5.js')

        # jQuery
        my_style = G.application.config.styleStore.getStyle(page.node.package.style)
        if my_style.hasValidConfig:
            if my_style.get_jquery() == True:
                #listFiles+=[self.scriptsDir/'exe_jquery.js']
                #listOutFiles+=[outputDir/'exe_jquery.js']
                jsFile = (self.scriptsDir/'exe_jquery.js')
                jsFile.copyfile(outputDir/'exe_jquery.js')
        else:
            #listFiles+=[self.scriptsDir/'exe_jquery.js']
            #listOutFiles+=[outputDir/'exe_jquery.js']
            jsFile = (self.scriptsDir/'exe_jquery.js')
            jsFile.copyfile(outputDir/'exe_jquery.js')

        if self.scormType == "commoncartridge" or self.scormType == "scorm2004" or self.scormType == "scorm1.2":
            listFiles=getFilesJSToMinify('scorm', self.scriptsDir)

        exportMinFileJS(listFiles, outputDir)

        if self.scormType == "scorm2004" or self.scormType == "scorm1.2":
            self.scriptsDir.copylist(('SCORM_API_wrapper.js',
                                      'SCOFunctions.js'), outputDir)

        # about SCHEMAS:
        schemasDir = ""
        if self.scormType == "scorm1.2":
            schemasDir = self.schemasDir/"scorm1.2"
            schemasDir.copylist(('imscp_rootv1p1p2.xsd',
                                'imsmd_rootv1p2p1.xsd',
                                'adlcp_rootv1p2.xsd',
                                'lom.xsd',
                                'lomCustom.xsd',
                                'ims_xml.xsd'), outputDir)
        elif self.scormType == "scorm2004":
            schemasDir = self.schemasDir/"scorm2004"
            schemasDir.copylist(('adlcp_v1p3.xsd',
                                'adlnav_v1p3.xsd',
                                'adlseq_v1p3.xsd',
                                'datatypes.dtd',
                                'imscp_v1p1.xsd',
                                'imsssp_v1p0.xsd',
                                'imsss_v1p0.xsd',
                                'imsss_v1p0auxresource.xsd',
                                'imsss_v1p0control.xsd',
                                'imsss_v1p0delivery.xsd',
                                'imsmd_rootv1p2p1.xsd',
                                'imsss_v1p0limit.xsd',
                                'imsss_v1p0objective.xsd',
                                'imsss_v1p0random.xsd',
                                'imsss_v1p0rollup.xsd',
                                'imsss_v1p0seqrule.xsd',
                                'imsss_v1p0util.xsd',
                                'ims_xml.xsd',
                                'lom.xsd',
                                'lomCustom.xsd',
                                'xml.xsd',
                                'XMLSchema.dtd'), outputDir)
            try:
                import shutil, errno
                shutil.copytree(schemasDir/"common", outputDir/"common")
                shutil.copytree(schemasDir/"extend", outputDir/"extend")
                shutil.copytree(schemasDir/"unique", outputDir/"unique")
                shutil.copytree(schemasDir/"vocab", outputDir/"vocab")
            except OSError as exc:
                if exc.errno == errno.ENOTDIR:
                    shutil.copy(schemasDir, outputDir)
                else: raise

        # copy players for media idevices.
        hasFlowplayer     = False
        hasMagnifier      = False
        hasXspfplayer     = False
        hasGallery        = False
        hasFX             = False
        hasSH             = False
        hasGames          = False
        hasElpLink        = False
        hasWikipedia      = False
        isBreak           = False
        hasInstructions   = False
        hasMediaelement   = False
        hasTooltips       = False
        hasABCMusic       = False
        listIdevicesFiles = []

        for page in self.pages:
            if isBreak:
                break
            for idevice in page.node.idevices:
                if (hasFlowplayer and hasMagnifier and hasXspfplayer and hasGallery and hasFX and hasSH and hasGames and hasElpLink and hasWikipedia and hasInstructions and hasMediaelement and hasTooltips and hasABCMusic):
                    isBreak = True
                    break
                if not hasFlowplayer:
                    if 'flowPlayer.swf' in idevice.systemResources:
                        hasFlowplayer = True
                if not hasMagnifier:
                    if 'mojomagnify.js' in idevice.systemResources:
                        hasMagnifier = True
                if not hasXspfplayer:
                    if 'xspf_player.swf' in idevice.systemResources:
                        hasXspfplayer = True
                if not hasGallery:
                    hasGallery = common.ideviceHasGallery(idevice)
                if not hasFX:
                    hasFX = common.ideviceHasFX(idevice)
                if not hasSH:
                    hasSH = common.ideviceHasSH(idevice)
                if not hasGames:
                    hasGames = common.ideviceHasGames(idevice)
                if not hasElpLink:
                    hasElpLink = common.ideviceHasElpLink(idevice,package)
                if not hasWikipedia:
                    if 'WikipediaIdevice' == idevice.klass:
                        hasWikipedia = True
                if not hasInstructions:
                    if 'TrueFalseIdevice' == idevice.klass or 'MultichoiceIdevice' == idevice.klass or 'VerdaderofalsofpdIdevice' == idevice.klass or 'EleccionmultiplefpdIdevice' == idevice.klass:
                        hasInstructions = True
                if not hasMediaelement:
                    hasMediaelement = common.ideviceHasMediaelement(idevice)
                if not hasTooltips:
                    hasTooltips = common.ideviceHasTooltips(idevice)
                if not hasABCMusic:
                    hasABCMusic = common.ideviceHasABCMusic(idevice)
                if hasattr(idevice, "_iDeviceDir"):
                    listIdevicesFiles.append((Path(idevice._iDeviceDir)/'export'))

            common.exportJavaScriptIdevicesFiles(page.node.idevices, outputDir);

        if hasFlowplayer:
            videofile = (self.templatesDir/'flowPlayer.swf')
            videofile.copyfile(outputDir/'flowPlayer.swf')
            controlsfile = (self.templatesDir/'flowplayer.controls.swf')
            controlsfile.copyfile(outputDir/'flowplayer.controls.swf')
        if hasMagnifier:
            videofile = (self.templatesDir/'mojomagnify.js')
            videofile.copyfile(outputDir/'mojomagnify.js')
        if hasXspfplayer:
            videofile = (self.templatesDir/'xspf_player.swf')
            videofile.copyfile(outputDir/'xspf_player.swf')
        if hasGallery:
            exeLightbox = (self.scriptsDir/'exe_lightbox')
            exeLightbox.copyfiles(outputDir)
        if hasFX:
            exeEffects = (self.scriptsDir/'exe_effects')
            exeEffects.copyfiles(outputDir)
        if hasSH:
            exeSH = (self.scriptsDir/'exe_highlighter')
            exeSH.copyfiles(outputDir)
        if hasGames:
            exeGames = (self.scriptsDir/'exe_games')
            exeGames.copyfiles(outputDir)
            # Add game js string to common_i18n
            langGameFile = open(outputDir + '/common_i18n.js', "a")
            langGameFile.write(common.getGamesJavaScriptStrings(False))
            langGameFile.close()
        if hasElpLink or package.get_exportElp():
            # Export the elp file
            currentPackagePath = Path(package.filename)
            currentPackagePath.copyfile(outputDir/package.name+'.elp')
        if hasWikipedia:
            wikipediaCSS = (self.cssDir/'exe_wikipedia.css')
            wikipediaCSS.copyfile(outputDir/'exe_wikipedia.css')
        if hasInstructions:
            common.copyFileIfNotInStyle('panel-amusements.png', self, outputDir)
            common.copyFileIfNotInStyle('stock-stop.png', self, outputDir)
        if hasMediaelement:
            mediaelement = (self.scriptsDir/'mediaelement')
            mediaelement.copyfiles(outputDir)
            if dT != "HTML5":
                jsFile = (self.scriptsDir/'exe_html5.js')
        if hasTooltips:
            exe_tooltips = (self.scriptsDir/'exe_tooltips')
            exe_tooltips.copyfiles(outputDir)
        if hasABCMusic:
            pluginScripts = (self.scriptsDir/'tinymce_4/js/tinymce/plugins/abcmusic/export')
            pluginScripts.copyfiles(outputDir)
        ext = ".html"
        if G.application.config.cutFileName == "1":
            ext = ".htm"

        if self.scormType == "scorm1.2" or self.scormType == "scorm2004":
            if package.license == "license GFDL":
                # include a copy of the GNU Free Documentation Licence
                (self.templatesDir/'fdl' + ext).copyfile(outputDir/'fdl' + ext)

        if hasattr(package, 'scowsinglepage') and package.scowsinglepage:
            page = SinglePage("singlepage_index", 1, package.root)
            page.save(outputDir/"singlepage_index" + ext)
            # Incluide eXe's icon if the Style doesn't have one
            themePath = Path(G.application.config.stylesDir/package.style)
            themeFavicon = themePath.joinpath("favicon.ico")
            if not themeFavicon.exists():
                faviconFile = (self.imagesDir/'favicon.ico')
                faviconFile.copyfile(outputDir/'favicon.ico')
        if hasattr(package, 'scowwebsite') and package.scowwebsite:
            website = WebsiteExport(self.config, self.styleDir, outputDir, "website_")
            website.export(package)
            (self.styleDir/'nav.css').copyfile(outputDir/'nav.css')
            # Incluide eXe's icon if the Style doesn't have one
            themePath = Path(G.application.config.stylesDir/package.style)
            themeFavicon = themePath.joinpath("favicon.ico")
            if not themeFavicon.exists():
                faviconFile = (self.imagesDir/'favicon.ico')
                faviconFile.copyfile(outputDir/'favicon.ico')
        if hasattr(package, 'exportSource') and package.exportSource:
            (G.application.config.webDir/'templates'/'content.xsd').copyfile(outputDir/'content.xsd')
            (outputDir/'content.data').write_bytes(encodeObject(package))
            (outputDir/'contentv3.xml').write_bytes(encodeObjectToXML(package))

        # Zip it up!
        self.filename.safeSave(self.doZip, _('EXPORT FAILED!\nLast succesful export is %s.'), outputDir)
        # Clean up the temporary dir
        outputDir.rmtree()


        return modifiedMetaData
    def __renderHeader(self):
		#TinyMCE lang (user preference)
        myPreferencesPage = self.webServer.preferences
        
        """Generates the header for AuthoringPage"""
        html  = common.docType()
        #################################################################################
        #################################################################################
        
        html += u'<html xmlns="http://www.w3.org/1999/xhtml" lang="'+myPreferencesPage.getSelectedLanguage()+'">\n'
        html += u'<head>\n'
        html += u"<link rel=\"stylesheet\" type=\"text/css\" href=\"/css/exe.css\" />"
        
        # Use the Style's base.css file if it exists
        themePath = Path(G.application.config.stylesDir/self.package.style)
        themeBaseCSS = themePath.joinpath("base.css")
        if themeBaseCSS.exists():
            html += u"<link rel=\"stylesheet\" type=\"text/css\" href=\"/style/%s/base.css\" />" % self.package.style
        else:
            html += u"<link rel=\"stylesheet\" type=\"text/css\" href=\"/style/base.css\" />"
            
        html += u"<link rel=\"stylesheet\" type=\"text/css\" href=\"/css/exe_wikipedia.css\" />"
        html += u"<link rel=\"stylesheet\" type=\"text/css\" href=\"/css/imgAreaSelect/imgareaselect-default.css\" />"
        html += u"<link rel=\"stylesheet\" type=\"text/css\" href=\"/style/%s/content.css\" />" % self.package.style
        html += u"<link rel=\"stylesheet\" type=\"text/css\" href=\"/css/jquery-ui-1.10.4.custom/ui-lightness/jquery-ui-1.10.4.custom.min.css\" />"
        if G.application.config.tinyMCEVersion != "4":
            html += u"<link rel='stylesheet' type='text/css' href='/scripts/tinymce_3.5.7/jscripts/tiny_mce/themes/advanced/skins/default/ui.css' />"
        if G.application.config.assumeMediaPlugins: 
            html += u"<script type=\"text/javascript\">var exe_assume_media_plugins = true;</script>\n"
        #JR: anado una variable con el estilo
        estilo = u'/style/%s/content.css' % self.package.style
        html += common.getJavaScriptStrings()
        html += u"<script type=\"text/javascript\">"
        html += u"var exe_style = '%s';" % estilo
        html += u"var exe_package_name='"+self.package.name+"';"
        html += 'var exe_export_format="'+common.getExportDocType()+'".toLowerCase();'
        html += 'var exe_editor_mode="'+myPreferencesPage.getEditorMode()+'";'
                
        
        #MD Set the correct tinymce version to use
        tinymce_src = None
        
        if G.application.config.tinyMCEVersion == "3":
            tinymce_src = {"wysiwyg_path" : 
                                "/scripts/tinymce_3.5.7/jscripts/tiny_mce/tiny_mce.js",
                           "wysiwyg_settings_path" :
                                "/scripts/tinymce_3.5.7_settings.js"}
        else:
            tinymce_src = {"wysiwyg_path" :
                            "/scripts/tinymce/tinymce.full.min.js",
                           "wysiwyg_settings_path" :
                            "/scripts/tinymce_settings.js"}
        html += 'var eXeLearning_settings = '
        html += json.dumps(tinymce_src) + ";\n"
        
        html += '</script>\n'
        html += u'<script type="text/javascript" src="../jsui/native.history.js"></script>\n'
        html += u'<script type="text/javascript" src="/scripts/authoring.js"></script>\n'
        html += u'<script type="text/javascript" src="/scripts/exe_jquery.js"></script>\n'
        html += u'<script type="text/javascript" src="/scripts/jquery-ui-1.10.4.custom.min.js"></script>\n'
        html += u'<script type="text/javascript" src="/scripts/exe_lightbox.js"></script>\n'
        html += u'<script type="text/javascript" src="/scripts/common.js"></script>\n'
        html += u'<script type="text/javascript" src="/scripts/jquery.imgareaselect.js"></script>\n'
        html += u'<script type="text/javascript" src="/scripts/exe_imgmaparea.js"></script>\n'
        html += u'<script type="text/javascript" src="/scripts/authoring_defaultprompts.js"></script>\n'
        html += u'<script type="text/javascript" src="/scripts/authoring_feedback_checkboxes.js"></script>\n'
        html += '<script type="text/javascript">document.write(unescape("%3Cscript src=\'" + eXeLearning_settings.wysiwyg_path + "\' type=\'text/javascript\'%3E%3C/script%3E"));</script>';
        html += '<script type="text/javascript">document.write(unescape("%3Cscript src=\'" + eXeLearning_settings.wysiwyg_settings_path + "\' type=\'text/javascript\'%3E%3C/script%3E"));</script>';
        html += u'<title>"+_("eXe : elearning XHTML editor")+"</title>\n'
        html += u'<meta http-equiv="content-type" content="text/html; '
        html += u' charset=UTF-8" />\n'
        html += u'</head>\n'
        return html
Beispiel #25
0
    def copyFiles(self, package, outputDir):
        """
        Copy all the files used by the website.
        """

        if os.path.isdir(self.stylesDir):
            # Copy the style files to the output dir
            styleFiles = [self.stylesDir / '..' / 'popup_bg.gif']
            styleFiles += self.stylesDir.files("*.*")
            self.stylesDir.copylist(styleFiles, outputDir)

        # copy the package's resource files
        for resourceFile in package.resourceDir.walkfiles():
            file = package.resourceDir.relpathto(resourceFile)

            if ("/" in file):
                Dir = Path(outputDir / file[:file.rindex("/")])

                if not Dir.exists():
                    Dir.makedirs()

                resourceFile.copy(outputDir / Dir)
            else:
                resourceFile.copy(outputDir)

        listCSSFiles = getFilesCSSToMinify('website', self.stylesDir)
        exportMinFileCSS(listCSSFiles, outputDir)

        # copy script files.
        my_style = G.application.config.styleStore.getStyle(package.style)
        # jQuery
        listFiles = []
        listOutFiles = []
        if my_style.hasValidConfig:
            if my_style.get_jquery() == True:
                jsFile = (self.scriptsDir / 'exe_jquery.js')
                jsFile.copyfile(outputDir / 'exe_jquery.js')
        else:
            listFiles += [self.scriptsDir / 'exe_jquery.js']
            listOutFiles += [outputDir / 'exe_jquery.js']

        # Minify common.js file
        listFiles = getFilesJSToMinify('website', self.scriptsDir)
        exportMinFileJS(listFiles, outputDir)

        # Create lang file
        langFile = open(outputDir + '/common_i18n.js', "w")
        langFile.write(common.getJavaScriptStrings(False))
        langFile.close()
        #dT = common.getExportDocType()
        dT = common.getExportDocType()
        if dT == "HTML5":
            jsFile = (self.scriptsDir / 'exe_html5.js')
            jsFile.copyfile(outputDir / 'exe_html5.js')

        # Incluide eXe's icon if the Style doesn't have one
        themePath = Path(G.application.config.stylesDir / package.style)
        themeFavicon = themePath.joinpath("favicon.ico")
        if not themeFavicon.exists():
            faviconFile = (self.imagesDir / 'favicon.ico')
            faviconFile.copyfile(outputDir / 'favicon.ico')

        # copy players for media idevices.
        hasFlowplayer = False
        hasMagnifier = False
        hasXspfplayer = False
        hasGallery = False
        hasFX = False
        hasSH = False
        hasGames = False
        hasWikipedia = False
        isBreak = False
        hasInstructions = False
        hasMediaelement = False
        hasTooltips = False
        hasABCMusic = False
        listIdevicesFiles = []

        for page in self.pages:
            if isBreak:
                break
            for idevice in page.node.idevices:
                if (hasFlowplayer and hasMagnifier and hasXspfplayer
                        and hasGallery and hasFX and hasSH and hasGames
                        and hasWikipedia and hasInstructions
                        and hasMediaelement and hasTooltips and hasABCMusic):
                    isBreak = True
                    break
                if not hasFlowplayer:
                    if 'flowPlayer.swf' in idevice.systemResources:
                        hasFlowplayer = True
                if not hasMagnifier:
                    if 'mojomagnify.js' in idevice.systemResources:
                        hasMagnifier = True
                if not hasXspfplayer:
                    if 'xspf_player.swf' in idevice.systemResources:
                        hasXspfplayer = True
                if not hasGallery:
                    hasGallery = common.ideviceHasGallery(idevice)
                if not hasFX:
                    hasFX = common.ideviceHasFX(idevice)
                if not hasSH:
                    hasSH = common.ideviceHasSH(idevice)
                if not hasGames:
                    hasGames = common.ideviceHasGames(idevice)
                if not hasWikipedia:
                    if 'WikipediaIdevice' == idevice.klass:
                        hasWikipedia = True
                if not hasInstructions:
                    if 'TrueFalseIdevice' == idevice.klass or 'MultichoiceIdevice' == idevice.klass or 'VerdaderofalsofpdIdevice' == idevice.klass or 'EleccionmultiplefpdIdevice' == idevice.klass:
                        hasInstructions = True
                if not hasMediaelement:
                    hasMediaelement = common.ideviceHasMediaelement(idevice)
                if not hasTooltips:
                    hasTooltips = common.ideviceHasTooltips(idevice)
                if not hasABCMusic:
                    hasABCMusic = common.ideviceHasABCMusic(idevice)
                if hasattr(idevice, "_iDeviceDir"):
                    listIdevicesFiles.append(
                        (Path(idevice._iDeviceDir) / 'export'))

        if hasFlowplayer:
            videofile = (self.templatesDir / 'flowPlayer.swf')
            videofile.copyfile(outputDir / 'flowPlayer.swf')
            controlsfile = (self.templatesDir / 'flowplayer.controls.swf')
            controlsfile.copyfile(outputDir / 'flowplayer.controls.swf')
        if hasMagnifier:
            videofile = (self.templatesDir / 'mojomagnify.js')
            videofile.copyfile(outputDir / 'mojomagnify.js')
        if hasXspfplayer:
            videofile = (self.templatesDir / 'xspf_player.swf')
            videofile.copyfile(outputDir / 'xspf_player.swf')
        if hasGallery:
            exeLightbox = (self.scriptsDir / 'exe_lightbox')
            exeLightbox.copyfiles(outputDir)
        if hasFX:
            exeEffects = (self.scriptsDir / 'exe_effects')
            exeEffects.copyfiles(outputDir)
        if hasSH:
            exeSH = (self.scriptsDir / 'exe_highlighter')
            exeSH.copyfiles(outputDir)
        if hasGames:
            exeGames = (self.scriptsDir / 'exe_games')
            exeGames.copyfiles(outputDir)
            # Add game js string to common_i18n
            langGameFile = open(outputDir + '/common_i18n.js', "a")
            langGameFile.write(common.getGamesJavaScriptStrings(False))
            langGameFile.close()
        if hasABCMusic:
            pluginScripts = (self.scriptsDir /
                             'tinymce_4/js/tinymce/plugins/abcmusic/export')
            pluginScripts.copyfiles(outputDir)
        if hasWikipedia:
            wikipediaCSS = (self.cssDir / 'exe_wikipedia.css')
            wikipediaCSS.copyfile(outputDir / 'exe_wikipedia.css')
        if hasInstructions:
            common.copyFileIfNotInStyle('panel-amusements.png', self,
                                        outputDir)
            common.copyFileIfNotInStyle('stock-stop.png', self, outputDir)
        if hasMediaelement:
            mediaelement = (self.scriptsDir / 'mediaelement')
            mediaelement.copyfiles(outputDir)
            dT = common.getExportDocType()
            if dT != "HTML5":
                jsFile = (self.scriptsDir / 'exe_html5.js')
                jsFile.copyfile(outputDir / 'exe_html5.js')
        if hasTooltips:
            exe_tooltips = (self.scriptsDir / 'exe_tooltips')
            exe_tooltips.copyfiles(outputDir)

        if hasattr(package, 'exportSource') and package.exportSource:
            (G.application.config.webDir / 'templates' /
             'content.xsd').copyfile(outputDir / 'content.xsd')
            (outputDir / 'content.data').write_bytes(encodeObject(package))
            (outputDir / 'contentv3.xml').write_bytes(
                encodeObjectToXML(package))
        ext = 'html'
        if G.application.config.cutFileName == "1":
            ext = 'htm'
        if package.license == "license GFDL":
            # include a copy of the GNU Free Documentation Licence
            (self.templatesDir / 'fdl' + '.' +
             ext).copyfile(outputDir / 'fdl' + '.' + ext)

        for iDeviceFiles in set(listIdevicesFiles):
            iDeviceFiles.copyfiles(outputDir)
Beispiel #26
0
    def process_previewed_images(self, content, page_id, idevice_id):
        """
        to build up the corresponding resources from any images (etc.) added
        in by the tinyMCE image-browser plug-in,
        which will have put them into src="../previews/"

        Now updated to include special math images as well, as generated
        by our custom exemath plugin to TinyMCE.  These are to follow the
        naming convention of "eXe_LaTeX_math_#.gif" (where the # is only
        guaranteed to be unique per Preview session, and can therefore end
        up being resource-ified into "eXe_LaTeX_math_#.#.gif"). Furthermore,
        they are to be paired with a source LateX file which is to be of
        the same name, followed by .tex, e.g., "eXe_LaTeX_math_#.gif.tex"
        (and to maintain this pairing, as a resource will need to be named
        "eXe_LaTeX_math_#.#.gif.tex" if applicable, where this does differ
        slightly from what could be its automatic unique-ified 
        resource-ification of: "eXe_LaTeX_math_#.gif.#.tex"!!!)
        """
        new_content = content

        # first, clear out any empty images.
        # Image and the new Math are unfortunately capable
        # of submitting an empty image, which will show as:
        #   <img src="/" />
        # (note that at least the media plugin still embeds a full 
        #  and valid empty-media tag, so no worries about them.)
        # These should be stopped in the plugin itself, but until then:
        empty_image_str = "<img src=\"/\" />"
        if new_content.find(empty_image_str) >= 0: 
            new_content = new_content.replace(empty_image_str, "");
            log.warn("Empty image tag(s) removed from content");


        # By this point, tinyMCE's javascript file browser handler:
        #         common.js's: chooseImage_viaTinyMCE() 
        # has already copied the file into the web-server's relative 
        # directory "/previews", BUT, something in tinyMCE's handler 
        # switches "/previews" to "../previews", so beware.....
        # 
        # At least it does NOT quote anything, and shows it as, for example: 
        #   <img src="../previews/%Users%r3m0w%Pictures%Remos_MiscPix% \
        #        SampleImage.JPG" height="161" width="215" /> 
        # old quoting-handling is still included in the following parsing,
        # which HAD allowed users to manually enter src= "file://..." URLs, 
        # but with the image now copied into previews, such URLS are no more.

        # DESIGN NOTE: eventually the following processing should be
        # enhanced to look at the HTML tags passed in, and ensure that
        # what is being found as 'src="../previews/.."' is really within
        # an IMG tag, etc.
        # For now, though, this easy parsing is working well:
        # JR        search_str = "src=\"../previews/" 
        search_str = "src=\"/previews/"
        # BEWARE OF THE ABOVE in regards to ProcessPreviewedMedia(),
        # which takes advantage of the fact that the embedded media
        # actually gets stored as src="previews/".
        # If this little weirdness of Images being stored as src="../previews/"
        # even changes to src="previews/", so more processing will be needed!

        found_pos = new_content.find(search_str) 
        while found_pos >= 0: 
            end_pos = new_content.find('\"', found_pos + len(search_str)) 
            if end_pos == -1: 
                # now unlikely that this has already been quoted out, 
                # since the search_str INCLUDES a \", but check anyway:
                end_pos = new_content.find('&quot', found_pos + 1) 
            else: 
                # okay, the end position \" was found, BUT beware of this 
                # strange case, where the image file:/// URLs 
                # were entered manually in one part of it 
                # (and therefore escaped to &quot), AND another quote occurs 
                # further below (perhaps even in a non-quoted file:/// via 
                # a tinyMCE browser, but really from anything!) 
                # So..... see if a &quot; is found in the file-name, and 
                # if so, back the end_pos up to there.  
                # NOTE: until actually looking at the HTML tags, and/or
                # we might be able to do this more programmatically by 
                # first seeing HOW the file:// is initially quoted, 
                # whether by a \" or by &quot;, but for now, 
                # just check this one.
                end_pos2 = new_content.find('&quot', found_pos + 1) 
                if end_pos2 > 0 and end_pos2 < end_pos:
                    end_pos = end_pos2
            if end_pos >= found_pos:
                # next, extract the actual file url, to be replaced later 
                # by the local resource file:
                file_url_str = new_content[found_pos:end_pos] 
                # and to get the actual file path, 
                # rather than the complete URL:

                # first compensate for how TinyMCE HTML-escapes accents:
                pre_input_file_name_str = file_url_str[len(search_str):]
                log.debug("ProcessPreviewedImages: found escaped file = " \
                           + pre_input_file_name_str)
                converter = HtmlToText(pre_input_file_name_str)
                input_file_name_str = converter.convertToText()

                log.debug("ProcessPreviewedImages: unescaped filename = " \
                           + input_file_name_str)

                webDir = Path(G.application.tempWebDir)
                previewDir = webDir.joinpath('previews')
                server_filename = previewDir.joinpath(input_file_name_str);

                # and now, extract just the filename string back out of that:
                file_name_str = server_filename.abspath().encode('utf-8');

                # Be sure to check that this file even exists before even 
                # attempting to create a corresponding GalleryImage resource:
                if os.path.exists(file_name_str) \
                and os.path.isfile(file_name_str): 
                    # Although full filenames (including flatted representations
                    # of their source directory tree) were used to help keep the
                    # filenames here in previewDir unique, this does cause
                    # problems with the filenames being too long, if they
                    # are kept that way.
                    # So.... if an optional .exe_info file is coupled to
                    # this one, go ahead and read in its original basename,
                    # in order to rename the file back to something shorter.
                    # After all, the resource process has its own uniqueifier.

                    # test for the optional .exe_info:
                    basename_value = os.path.basename(file_name_str)
                    descrip_file_path = Path(server_filename + ".exe_info")
                    if os.path.exists(descrip_file_path) \
                    and os.path.isfile(descrip_file_path): 
                        descrip_file = open(descrip_file_path, 'rb')
                        basename_info = descrip_file.read().decode('utf-8')
                        log.debug("ProcessPreviewedImages: decoded basename = " \
                            + basename_info)
                        # split out the value of this "basename=file" key 
                        basename_key_str = "basename="
                        basename_found_pos = basename_info.find(basename_key_str) 
                        # should be right there at the very beginning:
                        if basename_found_pos == 0: 
                            basename_value = \
                                   basename_info[len(basename_key_str):]
                    
                    #now we add the file to the package...
                    new_entry = self.add_user_file_to_idevice(idevice_id, file_name_str, 
                                                              new_basename = basename_value)
                    new_content = new_content.replace(file_url_str, "src=\"%s" % new_entry[1])
                    
            found_pos = new_content.find(search_str, found_pos + 1) 
    
        return new_content
Beispiel #27
0
class CmdlineExporter(object):
    extensions = {'xml': '.xml',
                  'scorm': '.zip',
                  'ims': '.zip',
                  'website': '',
                  'webzip': '.zip',
                  'singlepage': '',
                  'xliff': '.xlf'
                  }

    def __init__(self, config, options):
        self.config = config
        self.options = options
        self.web_dir = Path(self.config.webDir)
        self.styles_dir = None

    def do_export(self, inputf, outputf):
        if hasattr(self, 'export_' + self.options["export"]):
            LOG.debug("Exporting to type %s, in: %s, out: %s, overwrite: %s" \
            % (self.options["export"], inputf, outputf, str(self.options["overwrite"])))
            if not outputf:
                if self.options["export"] in ('website', 'singlepage'):
                    outputf = inputf.rsplit(".elp")[0]
                else:
                    outputf = inputf + self.extensions[self.options["export"]]
            outputfp = Path(outputf)
            if outputfp.exists() and not self.options["overwrite"]:
                error = _(u'"%s" already exists.\nPlease try again \
with a different filename') % outputf
                raise Exception(error.encode(sys.stdout.encoding))
            else:
                if outputfp.exists() and self.options["overwrite"]:
                    if outputfp.isdir():
                        for filen in outputfp.walkfiles():
                            filen.remove()
                        outputfp.rmdir()
                    else:
                        outputfp.remove()
                pkg = Package.load(inputf)
                LOG.debug("Package %s loaded" % (inputf))
                if not pkg:
                    error = _(u"Invalid input package")
                    raise Exception(error.encode(sys.stdout.encoding))
                self.styles_dir = self.web_dir.joinpath('style', pkg.style)
                LOG.debug("Styles dir: %s" % (self.styles_dir))
                getattr(self, 'export_' + self.options["export"])(pkg, outputf)
                return outputf
        else:
            raise Exception(_(u"Export format not implemented")\
.encode(sys.stdout.encoding))

    def export_xml(self, pkg, outputf):
        open(outputf, "w").write(encodeObjectToXML(pkg))

    def export_scorm(self, pkg, outputf):
        scormExport = ScormExport(self.config, self.styles_dir, outputf,
'scorm1.2')
        pkg.scowsinglepage = self.options['single-page']
        pkg.scowwebsite = self.options['website']
        pkg.scowsource = self.options['editable']
        scormExport.export(pkg)

    def export_scorm2004(self, pkg, outputf):
        scormExport = ScormExport(self.config, self.styles_dir, outputf,
'scorm2004')
        pkg.scowsinglepage = self.options['single-page']
        pkg.scowwebsite = self.options['website']
        pkg.scowsource = self.options['editable']
        scormExport.export(pkg)

    def export_ims(self, pkg, outputf):
        imsExport = IMSExport(self.config, self.styles_dir, outputf)
        imsExport.export(pkg)

    def export_website(self, pkg, outputf):
        outputfp = Path(outputf)
        outputfp.makedirs()
        websiteExport = WebsiteExport(self.config, self.styles_dir, outputf)
        websiteExport.export(pkg)

    def export_webzip(self, pkg, outputf):
        websiteExport = WebsiteExport(self.config, self.styles_dir, outputf)
        websiteExport.exportZip(pkg)

    def export_singlepage(self, pkg, outputf, print_flag=0):
        images_dir = self.web_dir.joinpath('images')
        scripts_dir = self.web_dir.joinpath('scripts')
        css_dir = self.web_dir.joinpath('css')
        templates_dir = self.web_dir.joinpath('templates')
        singlePageExport = SinglePageExport(self.styles_dir, outputf, \
                             images_dir, scripts_dir, css_dir, templates_dir)
        singlePageExport.export(pkg, print_flag)

    def export_xliff(self, pkg, outputf):
        xliff = XliffExport(self.config, outputf, \
                            source_copied_in_target=self.options["copy-source"], \
                            wrap_cdata=self.options["wrap-cdata"])
        xliff.export(pkg)
Beispiel #28
0
 def handleTinyMCEimageChoice(
     self, client, tinyMCEwin, tinyMCEwin_name, tinyMCEfield, local_filename, preview_filename
 ):
     """
     Once an image is selected in the file browser that is spawned by the 
     TinyMCE image dialog, copy this file (which is local to the user's 
     machine) into the server space, under a preview directory 
     (after checking if this exists, and creating it if necessary).
     Note that this IS a "cheat", in violation of the client-server 
     separation, but can be done since we know that the eXe server is 
     actually sitting on the client host.
     """
     server_filename = ""
     callback_errors = ""
     errors = 0
     log.debug(
         "handleTinyMCEimageChoice: image local = " + local_filename + ", base=" + os.path.basename(local_filename)
     )
     webDir = Path(G.application.tempWebDir)
     previewDir = webDir.joinpath("previews")
     if not previewDir.exists():
         log.debug("image previews directory does not yet exist; " + "creating as %s " % previewDir)
         previewDir.makedirs()
     elif not previewDir.isdir():
         client.alert(_(u"Preview directory %s is a file, cannot replace it") % previewDir)
         log.error(
             "Couldn't preview tinyMCE-chosen image: " + "Preview dir %s is a file, cannot replace it" % previewDir
         )
         callback_errors = "Preview dir is a file, cannot replace"
         errors += 1
     if errors == 0:
         log.debug("handleTinyMCEimageChoice: originally, local_filename=" + local_filename)
         local_filename = unicode(local_filename, "utf-8")
         log.debug("handleTinyMCEimageChoice: in unicode, local_filename=" + local_filename)
         localImagePath = Path(local_filename)
         log.debug("handleTinyMCEimageChoice: after Path, localImagePath= " + localImagePath)
         if not localImagePath.exists() or not localImagePath.isfile():
             client.alert(_(u"Local file %s is not found, cannot preview it") % localImagePath)
             log.error("Couldn't find tinyMCE-chosen image: %s" % localImagePath)
             callback_errors = "Image file %s not found, cannot preview" % localImagePath
             errors += 1
     try:
         log.debug("URIencoded preview filename=" + preview_filename)
         server_filename = previewDir.joinpath(preview_filename)
         log.debug(
             "handleTinyMCEimageChoice copying image from '"
             + local_filename
             + "' to '"
             + server_filename.abspath()
             + "'."
         )
         shutil.copyfile(local_filename, server_filename.abspath())
         descrip_file_path = Path(server_filename + ".exe_info")
         log.debug(
             "handleTinyMCEimageChoice creating preview " + "description file '" + descrip_file_path.abspath() + "'."
         )
         descrip_file = open(descrip_file_path, "wb")
         unspaced_filename = local_filename.replace(" ", "_")
         unhashed_filename = unspaced_filename.replace("#", "_num_")
         unamped_local_filename = unhashed_filename.replace("&", "_and_")
         log.debug("and setting new file basename as: " + unamped_local_filename)
         my_basename = os.path.basename(unamped_local_filename)
         descrip_file.write((u"basename=" + my_basename).encode("utf-8"))
         descrip_file.flush()
         descrip_file.close()
     except Exception, e:
         client.alert(_("SAVE FAILED!\n%s" % str(e)))
         log.error(
             "handleTinyMCEimageChoice unable to copy local image " + "file to server prevew, error = " + str(e)
         )
         raise
Beispiel #29
0
    def copyFiles(self, package, outputDir):
        """
        Copy all the files used by the website.
        """

        if os.path.isdir(self.stylesDir):
            # Copy the style sheet files to the output dir
            styleFiles = [self.stylesDir / '..' / 'base.css']
            styleFiles += [self.stylesDir / '..' / 'popup_bg.gif']
            styleFiles += self.stylesDir.files("*.css")
            styleFiles += self.stylesDir.files("*.jpg")
            styleFiles += self.stylesDir.files("*.gif")
            styleFiles += self.stylesDir.files("*.png")
            styleFiles += self.stylesDir.files("*.js")
            styleFiles += self.stylesDir.files("*.html")
            styleFiles += self.stylesDir.files("*.ico")
            styleFiles += self.stylesDir.files("*.ttf")
            styleFiles += self.stylesDir.files("*.eot")
            styleFiles += self.stylesDir.files("*.otf")
            styleFiles += self.stylesDir.files("*.woff")
            self.stylesDir.copylist(styleFiles, outputDir)

        # copy the package's resource files
        package.resourceDir.copyfiles(outputDir)

        # copy script files.
        my_style = G.application.config.styleStore.getStyle(package.style)
        # jQuery
        if my_style.hasValidConfig:
            if my_style.get_jquery() == True:
                jsFile = (self.scriptsDir / 'exe_jquery.js')
                jsFile.copyfile(outputDir / 'exe_jquery.js')
        else:
            jsFile = (self.scriptsDir / 'exe_jquery.js')
            jsFile.copyfile(outputDir / 'exe_jquery.js')

        jsFile = (self.scriptsDir / 'common.js')
        jsFile.copyfile(outputDir / 'common.js')
        #dT = common.getExportDocType()
        dT = common.getExportDocType()
        if dT == "HTML5":
            jsFile = (self.scriptsDir / 'exe_html5.js')
            jsFile.copyfile(outputDir / 'exe_html5.js')

        # Incluide eXe's icon if the Style doesn't have one
        themePath = Path(G.application.config.stylesDir / package.style)
        themeFavicon = themePath.joinpath("favicon.ico")
        if not themeFavicon.exists():
            faviconFile = (self.imagesDir / 'favicon.ico')
            faviconFile.copyfile(outputDir / 'favicon.ico')

        # copy players for media idevices.
        hasFlowplayer = False
        hasMagnifier = False
        hasXspfplayer = False
        hasGallery = False
        hasFX = False
        hasSH = False
        hasGames = False
        hasWikipedia = False
        isBreak = False
        hasInstructions = False
        hasMediaelement = False
        hasTooltips = False

        for page in self.pages:
            if isBreak:
                break
            for idevice in page.node.idevices:
                if (hasFlowplayer and hasMagnifier and hasXspfplayer
                        and hasGallery and hasFX and hasSH and hasGames
                        and hasWikipedia and hasInstructions
                        and hasMediaelement and hasTooltips):
                    isBreak = True
                    break
                if not hasFlowplayer:
                    if 'flowPlayer.swf' in idevice.systemResources:
                        hasFlowplayer = True
                if not hasMagnifier:
                    if 'mojomagnify.js' in idevice.systemResources:
                        hasMagnifier = True
                if not hasXspfplayer:
                    if 'xspf_player.swf' in idevice.systemResources:
                        hasXspfplayer = True
                if not hasGallery:
                    hasGallery = common.ideviceHasGallery(idevice)
                if not hasFX:
                    hasFX = common.ideviceHasFX(idevice)
                if not hasSH:
                    hasSH = common.ideviceHasSH(idevice)
                if not hasGames:
                    hasGames = common.ideviceHasGames(idevice)
                if not hasWikipedia:
                    if 'WikipediaIdevice' == idevice.klass:
                        hasWikipedia = True
                if not hasInstructions:
                    if 'TrueFalseIdevice' == idevice.klass or 'MultichoiceIdevice' == idevice.klass or 'VerdaderofalsofpdIdevice' == idevice.klass or 'EleccionmultiplefpdIdevice' == idevice.klass:
                        hasInstructions = True
                if not hasMediaelement:
                    hasMediaelement = common.ideviceHasMediaelement(idevice)
                if not hasTooltips:
                    hasTooltips = common.ideviceHasTooltips(idevice)

        if hasFlowplayer:
            videofile = (self.templatesDir / 'flowPlayer.swf')
            videofile.copyfile(outputDir / 'flowPlayer.swf')
            controlsfile = (self.templatesDir / 'flowplayer.controls.swf')
            controlsfile.copyfile(outputDir / 'flowplayer.controls.swf')
        if hasMagnifier:
            videofile = (self.templatesDir / 'mojomagnify.js')
            videofile.copyfile(outputDir / 'mojomagnify.js')
        if hasXspfplayer:
            videofile = (self.templatesDir / 'xspf_player.swf')
            videofile.copyfile(outputDir / 'xspf_player.swf')
        if hasGallery:
            exeLightbox = (self.scriptsDir / 'exe_lightbox')
            exeLightbox.copyfiles(outputDir)
        if hasFX:
            exeEffects = (self.scriptsDir / 'exe_effects')
            exeEffects.copyfiles(outputDir)
        if hasSH:
            exeSH = (self.scriptsDir / 'exe_highlighter')
            exeSH.copyfiles(outputDir)
        if hasGames:
            exeGames = (self.scriptsDir / 'exe_games')
            exeGames.copyfiles(outputDir)
        if hasWikipedia:
            wikipediaCSS = (self.cssDir / 'exe_wikipedia.css')
            wikipediaCSS.copyfile(outputDir / 'exe_wikipedia.css')
        if hasInstructions:
            common.copyFileIfNotInStyle('panel-amusements.png', self,
                                        outputDir)
            common.copyFileIfNotInStyle('stock-stop.png', self, outputDir)
        if hasMediaelement:
            mediaelement = (self.scriptsDir / 'mediaelement')
            mediaelement.copyfiles(outputDir)
            dT = common.getExportDocType()
            if dT != "HTML5":
                jsFile = (self.scriptsDir / 'exe_html5.js')
                jsFile.copyfile(outputDir / 'exe_html5.js')
        if hasTooltips:
            exe_tooltips = (self.scriptsDir / 'exe_tooltips')
            exe_tooltips.copyfiles(outputDir)

        if hasattr(package, 'exportSource') and package.exportSource:
            (G.application.config.webDir / 'templates' /
             'content.xsd').copyfile(outputDir / 'content.xsd')
            (outputDir / 'content.data').write_bytes(encodeObject(package))
            (outputDir / 'contentv3.xml').write_bytes(
                encodeObjectToXML(package))

        if package.license == "license GFDL":
            # include a copy of the GNU Free Documentation Licence
            (self.templatesDir / 'fdl.html').copyfile(outputDir / 'fdl.html')
    def copyFiles(self, package):
        """
        Copy all the files used by the website.
        """
        # Copy the style sheet files to the output dir
        # But not nav.css
        if os.path.isdir(self.stylesDir):
            # Copy the style sheet files to the output dir
            styleFiles = [self.stylesDir / '..' / 'base.css']
            styleFiles += [self.stylesDir / '..' / 'popup_bg.gif']
            styleFiles += self.stylesDir.files("*.css")
            if "nav.css" in styleFiles:
                styleFiles.remove("nav.css")
            styleFiles += self.stylesDir.files("*.jpg")
            styleFiles += self.stylesDir.files("*.gif")
            styleFiles += self.stylesDir.files("*.png")
            styleFiles += self.stylesDir.files("*.js")
            styleFiles += self.stylesDir.files("*.html")
            styleFiles += self.stylesDir.files("*.ico")
            styleFiles += self.stylesDir.files("*.ttf")
            styleFiles += self.stylesDir.files("*.eot")
            styleFiles += self.stylesDir.files("*.otf")
            styleFiles += self.stylesDir.files("*.woff")
            self.stylesDir.copylist(styleFiles, self.outputDir)

        # copy the package's resource files
        package.resourceDir.copyfiles(self.outputDir)

        # copy script files.
        my_style = G.application.config.styleStore.getStyle(package.style)

        # jQuery
        if my_style.hasValidConfig:
            if my_style.get_jquery() == True:
                jsFile = (self.scriptsDir / 'exe_jquery.js')
                jsFile.copyfile(self.outputDir / 'exe_jquery.js')
        else:
            jsFile = (self.scriptsDir / 'exe_jquery.js')
            jsFile.copyfile(self.outputDir / 'exe_jquery.js')

        jsFile = (self.scriptsDir / 'common.js')
        jsFile.copyfile(self.outputDir / 'common.js')
        jsFile = (self.scriptsDir / 'lernmodule_net.js')
        jsFile.copyfile(self.outputDir / 'lernmodule_net.js')
        jsFile = (self.scriptsDir / 'lernmodule_net_custom.js')
        jsFile.copyfile(self.outputDir / 'lernmodule_net_custom.js')
        dT = common.getExportDocType()
        if dT == "HTML5":
            jsFile = (self.scriptsDir / 'exe_html5.js')
            jsFile.copyfile(self.outputDir / 'exe_html5.js')

        # Incluide eXe's icon if the Style doesn't have one
        themePath = Path(G.application.config.stylesDir / package.style)
        themeFavicon = themePath.joinpath("favicon.ico")
        if not themeFavicon.exists():
            faviconFile = (self.imagesDir / 'favicon.ico')
            faviconFile.copyfile(self.outputDir / 'favicon.ico')

        #JR Metemos los reproductores necesarios
        self.compruebaReproductores(self.page.node)

        if package.license == "license GFDL":
            # include a copy of the GNU Free Documentation Licence
            (self.templatesDir / 'fdl.html').copyfile(self.outputDir /
                                                      'fdl.html')
Beispiel #31
0
    def convertToFreeText(self):
        """
        Actually do the Converting of 
              MathsIdevice -> FreeTextIdevice,
        now that FreeText can hold embeddded images.
        """
        new_content = ""

        # ensure that an image resource still exists on this ImageWithText,
        # before trying to add it into the FreeText idevice.
        # Why?  corrupt packages have been seen missing resources...
        # (usually in with extra package objects as well, probably
        # from old code doing faulty Extracts, or somesuch nonesense)
        imageResource_exists = False

        if not self.content.gifResource is None:
            if os.path.exists(self.content.gifResource.path) and \
            os.path.isfile(self.content.gifResource.path):
                imageResource_exists = True
            else:
                log.warn("Couldn't find Maths image when upgrading "\
                        + self.content.gifResource.storageName)

        if imageResource_exists:
            new_content += "<img src=\"resources/" \
                    + self.content.gifResource.storageName + "\" "
            # create the expected math resource url for comparison later,
            # once we do actually create it:
            math_resource_url="resources/" \
                    + self.content.gifResource.storageName + ".tex\" "
            new_content += "exe_math_latex=\"" + math_resource_url + "\" "
            new_content += "exe_math_size=\"" + repr(self.content.fontsize) \
                    + "\" "
            # no height or width for math images, eh? nope.
            new_content += "/> \n"

        elif self.content.gifResource:
            new_content += "<BR>\n[WARNING: missing image: " \
                    + self.content.gifResource.storageName + "]\n"

        replacementIdev = FreeTextIdevice(new_content)

        ###########
        # now, copy that content field's content into its _w_resourcePaths,
        # and properly remove the resource directory via Massage....
        # for its _wo_resourcePaths:
        # note that replacementIdev's content field's content
        # is automatically set at its constructor (above),
        # as is the default content_w_resourcePaths (a copy of content)
        # AND the default content_wo_resourcePaths (a copy of content),
        # so only need to update the content_wo_resourcePaths:
        replacementIdev.content.content_wo_resourcePaths = \
                replacementIdev.content.MassageContentForRenderView( \
                    replacementIdev.content.content_w_resourcePaths)
        # Design note: ahhhhh, the above is a good looking reason to possibly
        # have the MassageContentForRenderView() method
        # just assume its content_w_resourcePaths as the input
        # and write the output to its content_wo_resourcePaths.....
        #######

        # next step, add the new IDevice into the same node as this one
        self.parentNode.addIdevice(replacementIdev)

        # in passing GalleryImage into the FieldWithResources,
        # that content field needs to be sure to have an updated
        # parentNode, courtesy of its idevice:
        replacementIdev.content.setParentNode()

        # and semi-manually add/create the current image
        # resource into the FreeTextIdevice's TextAreaField, content.
        # the content text will have already been taken care of above,
        # including the ideal <img src=...> including resources path,
        # but still need the actual image resource:

        if imageResource_exists:
            # Not sure why this can't be imported up top, but it gives
            # ImportError: cannot import name GalleryImages,
            # so here it be:
            from exe.engine.galleryidevice import GalleryImage

            full_image_path = self.content.gifResource.path
            # with empty caption:
            new_GalleryImage = GalleryImage(replacementIdev.content, \
                    '',  full_image_path, mkThumbnail=False)

            # and....  write the latex_source out into the preview_math_srcfile
            # such that it can then be passed into the compile command.
            # Using the desired name (image.gif.tex), write it into tempWebDir:
            webDir = Path(G.application.tempWebDir)
            source_tex_name = self.content.gifResource.storageName + ".tex"
            math_path = webDir.joinpath(source_tex_name)
            math_filename_str = math_path.abspath().encode('utf-8')

            log.debug("convertToFreeText: writing LaTeX source into \'" \
                                        + math_filename_str + "\'.")
            math_file = open(math_filename_str, 'wb')
            # do we need to append a \n here?:
            math_file.write(self.content.latex)
            math_file.flush()
            math_file.close()

            # finally, creating a resource for the latex_source as well:
            new_GalleryLatex = GalleryImage(replacementIdev.content, \
                    '', math_filename_str, mkThumbnail=False)
            new_GalleryLatexResource = new_GalleryLatex._imageResource
            mathsrc_resource_path = new_GalleryLatexResource._storageName
            # and re-concatenate from the global resources name,
            # to build the webUrl to the resource:
            mathsrc_resource_url = new_GalleryLatex.resourcesUrl \
                    + mathsrc_resource_path

            # AND compare with the newly built resource_url from above,
            # to ensure that we've got what we had expected, jah!
            if (mathsrc_resource_url != math_resource_url):
                log.warn('The math source was resource-ified differently ' \
                        + 'than expected, to: ' + mathsrc_resource_url \
                        + '; the source will need to be recreated.')
                # right. we COULD go ahead and change the exe_math_latex
                # attribute to point to the actual mathsrc_resource_url,
                # EXCEPT that the entire exemath plugin is currently built
                # with the idea that the source .tex file will always be named
                # as the mathimage.gif.tex, and this exe_math_latex tag
                # is really just letting the rest of the world know that
                # there IS corresponding source expected there.
                # If exemath is to ever change and use the actual contents
                # of this exe_math_latex tag (rather than just appended .tex),
                # then this could be revisited here.

            else:
                log.debug('math source was resource-ified properly to: ' \
                        + mathsrc_resource_url)

        # and move the new idevice up to the position following this node!
        while ( self.parentNode.idevices.index(replacementIdev) \
                > ( (self.parentNode.idevices.index(self) + 1))):
            replacementIdev.movePrev()

        # finally: delete THIS idevice itself, deleting it from the node
        self.delete()
Beispiel #32
0
class CmdlineExporter(object):
    extensions = {
        'xml': '.xml',
        'scorm': '.zip',
        'ims': '.zip',
        'website': '',
        'webzip': '.zip',
        'singlepage': '',
        'xliff': '.xlf'
    }

    def __init__(self, config, options):
        self.config = config
        self.options = options
        self.web_dir = Path(self.config.webDir)
        self.styles_dir = None

    def do_export(self, inputf, outputf):
        if hasattr(self, 'export_' + self.options["export"]):
            LOG.debug("Exporting to type %s, in: %s, out: %s, overwrite: %s" \
            % (self.options["export"], inputf, outputf, str(self.options["overwrite"])))
            if not outputf:
                if self.options["export"] in ('website', 'singlepage'):
                    outputf = inputf.rsplit(".elp")[0]
                else:
                    outputf = inputf + self.extensions[self.options["export"]]
            outputfp = Path(outputf)
            if outputfp.exists() and not self.options["overwrite"]:
                error = _(u'"%s" already exists.\nPlease try again \
with a different filename') % outputf
                raise Exception(error.encode(sys.stdout.encoding))
            else:
                if outputfp.exists() and self.options["overwrite"]:
                    if outputfp.isdir():
                        for filen in outputfp.walkfiles():
                            filen.remove()
                        outputfp.rmdir()
                    else:
                        outputfp.remove()
                pkg = Package.load(inputf)
                LOG.debug("Package %s loaded" % (inputf))
                if not pkg:
                    error = _(u"Invalid input package")
                    raise Exception(error.encode(sys.stdout.encoding))
                self.styles_dir = self.web_dir.joinpath('style', pkg.style)
                LOG.debug("Styles dir: %s" % (self.styles_dir))
                getattr(self, 'export_' + self.options["export"])(pkg, outputf)
                return outputf
        else:
            raise Exception(_(u"Export format not implemented")\
.encode(sys.stdout.encoding))

    def export_xml(self, pkg, outputf):
        open(outputf, "w").write(encodeObjectToXML(pkg))

    def export_scorm(self, pkg, outputf):
        scormExport = ScormExport(self.config, self.styles_dir, outputf,
                                  'scorm1.2')
        pkg.scowsinglepage = self.options['single-page']
        pkg.scowwebsite = self.options['website']
        pkg.scowsource = self.options['editable']
        scormExport.export(pkg)

    def export_ims(self, pkg, outputf):
        imsExport = IMSExport(self.config, self.styles_dir, outputf)
        imsExport.export(pkg)

    def export_website(self, pkg, outputf):
        outputfp = Path(outputf)
        outputfp.makedirs()
        websiteExport = WebsiteExport(self.config, self.styles_dir, outputf)
        websiteExport.export(pkg)

    def export_webzip(self, pkg, outputf):
        websiteExport = WebsiteExport(self.config, self.styles_dir, outputf)
        websiteExport.exportZip(pkg)

    def export_singlepage(self, pkg, outputf, print_flag=0):
        images_dir = self.web_dir.joinpath('images')
        scripts_dir = self.web_dir.joinpath('scripts')
        templates_dir = self.web_dir.joinpath('templates')
        singlePageExport = SinglePageExport(self.styles_dir, outputf, \
                             images_dir, scripts_dir, templates_dir)
        singlePageExport.export(pkg, print_flag)

    def export_xliff(self, pkg, outputf):
        xliff = XliffExport(self.config, outputf, \
                            source_copied_in_target=self.options["copy-source"], \
                            wrap_cdata=self.options["wrap-cdata"])
        xliff.export(pkg)
    def copyFiles(self, package):
        """
        Copy all the files used by the website.
        """
        # Copy the style sheet files to the output dir
        # But not nav.css
        if os.path.isdir(self.stylesDir):
            # Copy the style sheet files to the output dir
            styleFiles  = [self.stylesDir/'..'/'base.css']
            styleFiles += [self.stylesDir/'..'/'popup_bg.gif']
            styleFiles += self.stylesDir.files("*.css")
            if "nav.css" in styleFiles:
                styleFiles.remove("nav.css")
            styleFiles += self.stylesDir.files("*.jpg")
            styleFiles += self.stylesDir.files("*.gif")
            styleFiles += self.stylesDir.files("*.png")
            styleFiles += self.stylesDir.files("*.js")
            styleFiles += self.stylesDir.files("*.html")
            styleFiles += self.stylesDir.files("*.ico")
            styleFiles += self.stylesDir.files("*.ttf")
            styleFiles += self.stylesDir.files("*.eot")
            styleFiles += self.stylesDir.files("*.otf")
            styleFiles += self.stylesDir.files("*.woff")
            self.stylesDir.copylist(styleFiles, self.outputDir)
            
        # copy the package's resource files
        package.resourceDir.copyfiles(self.outputDir)

        # copy script files.
        my_style = G.application.config.styleStore.getStyle(package.style)
        
        # jQuery
        if my_style.hasValidConfig:
            if my_style.get_jquery() == True:
                jsFile = (self.scriptsDir/'exe_jquery.js')
                jsFile.copyfile(self.outputDir/'exe_jquery.js')
        else:
            jsFile = (self.scriptsDir/'exe_jquery.js')
            jsFile.copyfile(self.outputDir/'exe_jquery.js')
            
        jsFile = (self.scriptsDir/'common.js')
        jsFile.copyfile(self.outputDir/'common.js')
        jsFile = (self.scriptsDir/'lernmodule_net.js')
        jsFile.copyfile(self.outputDir/'lernmodule_net.js')
        dT = common.getExportDocType()
        if dT == "HTML5":
            jsFile = (self.scriptsDir/'exe_html5.js')
            jsFile.copyfile(self.outputDir/'exe_html5.js')
            
        # Incluide eXe's icon if the Style doesn't have one
        themePath = Path(G.application.config.stylesDir/package.style)
        themeFavicon = themePath.joinpath("favicon.ico")
        if not themeFavicon.exists():
            faviconFile = (self.imagesDir/'favicon.ico')
            faviconFile.copyfile(self.outputDir/'favicon.ico')

        #JR Metemos los reproductores necesarios
        self.compruebaReproductores(self.page.node)


        if package.license == "license GFDL":
            # include a copy of the GNU Free Documentation Licence
            (self.templatesDir/'fdl.html').copyfile(self.outputDir/'fdl.html')
Beispiel #34
0
def ideviceHeader(e, style, mode):
    dT = getExportDocType()
    lb = "\n"  # Line breaks
    # Default HTML tags:
    sectionTag = "div"
    articleTag = "div"
    headerTag = "div"
    titleTag = "h2"
    if dT == "HTML5":
        sectionTag = "section"
        articleTag = "article"
        headerTag = "header"
        titleTag = "h1"

    themePath = Path(G.application.config.stylesDir / style)
    themeXMLFile = themePath.joinpath("config.xml")
    themeHasXML = themeHasConfigXML(style)

    w = ""  # Common wrapper
    o = ""  # Old HTML (themes with no config.xml file)
    h = ""  # New HTML
    w2 = ""
    eEm = ""
    if e.idevice.emphasis > 0:
        w2 = "<" + sectionTag + ' class="iDevice_inner">' + lb
        w2 += "<" + sectionTag + ' class="iDevice_content_wrapper">' + lb
        eEm = " em_iDevice"

    if mode == "preview" and themeHasXML:
        w += "<" + sectionTag + ' class="iDevice_wrapper ' + e.idevice.klass + eEm + '" id="id' + e.id + '">' + lb

    w += u"<" + articleTag + ' class="iDevice emphasis' + unicode(e.idevice.emphasis) + '" '
    if mode == "preview":
        w += u"ondblclick=\"submitLink('edit', " + e.id + ', 0);"'
    w += ">" + lb

    if e.idevice.emphasis > 0:
        h += "<" + headerTag + ' class="iDevice_header"'
        if e.idevice.icon:
            displayIcon = True
            # The following lines should be replaced by something like:
            """
            if hasattr(e.idevice, 'originalicon'):
                if e.idevice.icon==e.idevice.originalicon:
                    displayIcon = False
            """
            k = e.idevice.klass
            i = e.idevice.icon
            if (
                (k == "ListaIdevice" and i == "question")
                or (k == "CasestudyIdevice" and i == "casestudy")
                or (k == "GalleryIdevice" and i == "gallery")
                or (k == "ClozeIdevice" and i == "question")
                or (k == "ReflectionIdevice" and i == "reflection")
                or (k == "QuizTestIdevice" and i == "question")
                or (k == "TrueFalseIdevice" and i == "question")
                or (k == "MultiSelectIdevice" and i == "question")
                or (k == "MultichoiceIdevice" and i == "question")
            ):
                displayIcon = False
            # /end
            iconPath = "/style/" + style + "/icon_" + e.idevice.icon + ".gif"
            if mode == "view":
                iconPath = "icon_" + e.idevice.icon + ".gif"
            myIcon = themePath.joinpath("icon_" + e.idevice.icon + ".gif")
            if myIcon.exists():
                o += u'<img alt="" class="iDevice_icon" src="' + iconPath + '" />'
            if (e.idevice.icon + "Idevice") != e.idevice.klass:
                if myIcon.exists() and displayIcon:
                    h += ' style="background-image:url(' + iconPath + ')"'
        else:
            log.debug("Idevice %s at node %s has no icon" % (e.idevice._title, e.idevice.parentNode._title))
        t = e.idevice.title
        fullT = u"<" + titleTag + ' class="iDeviceTitle">' + t + "</" + titleTag + ">"
        if t == "":
            fullT = u'<span class="iDeviceTitle">&nbsp;</span>'
        o += u"<" + titleTag + ' class="iDeviceTitle">' + t + "</" + titleTag + ">"
        h += ">"
        h += fullT
        h += "</" + headerTag + ">" + lb

    if e.idevice.emphasis <= 0:
        h = ""
        o = ""
    if themeHasXML:
        return w + h + w2
    else:
        return w + o + w2
Beispiel #35
0
    def copyFiles(self, package):
        """
        Copy all the files used by the website.
        """
        # Copy the style files to the output dir
        # But not nav.css
        if os.path.isdir(self.stylesDir):
            styleFiles = [self.stylesDir/'..'/'popup_bg.gif']
            styleFiles += self.stylesDir.files("*.*")
            if "nav.css" in styleFiles:
                styleFiles.remove("nav.css")
            self.stylesDir.copylist(styleFiles, self.outputDir)

        # copy the package's resource files
        for resourceFile in package.resourceDir.walkfiles():
            file = package.resourceDir.relpathto(resourceFile)

            if ("/" in file):
                Dir = Path(self.outputDir/file[:file.rindex("/")])

                if not Dir.exists():
                    Dir.makedirs()

                resourceFile.copy(self.outputDir/Dir)
            else:
                resourceFile.copy(self.outputDir)

        listCSSFiles=getFilesCSSToMinify('singlepage', self.stylesDir)
        exportMinFileCSS(listCSSFiles, self.outputDir)

        # copy script files.
        my_style = G.application.config.styleStore.getStyle(package.style)

        # jQuery
        if my_style.hasValidConfig:
            if my_style.get_jquery() == True:
                jsFile = (self.scriptsDir/'exe_jquery.js')
                jsFile.copyfile(self.outputDir/'exe_jquery.js')
        else:
            jsFile = (self.scriptsDir/'exe_jquery.js')
            jsFile.copyfile(self.outputDir/'exe_jquery.js')

        dT = common.getExportDocType()
        if dT == "HTML5":
            jsFile = (self.scriptsDir/'exe_html5.js')
            jsFile.copyfile(self.outputDir/'exe_html5.js')

        # Minify common.js file
        listFiles=getFilesJSToMinify('singlepage', self.scriptsDir)
        exportMinFileJS(listFiles, self.outputDir)

        # Create lang file
        langFile = open(self.outputDir + '/common_i18n.js', "w")
        langFile.write(common.getJavaScriptStrings(False))
        langFile.close()

        # Incluide eXe's icon if the Style doesn't have one
        themePath = Path(G.application.config.stylesDir/package.style)
        themeFavicon = themePath.joinpath("favicon.ico")
        if not themeFavicon.exists():
            faviconFile = (self.imagesDir/'favicon.ico')
            faviconFile.copyfile(self.outputDir/'favicon.ico')

        #JR Metemos los reproductores necesarios
        self.compruebaReproductores(self.page.node)


        if package.license == "license GFDL":
            # include a copy of the GNU Free Documentation Licence
            ext = 'html'
            if G.application.config.cutFileName == "1":
                ext = 'htm'
            (self.templatesDir/'fdl' + '.' + ext).copyfile(self.outputDir/'fdl' + '.' + ext)
Beispiel #36
0
    def handleTinyMCEmath(self, client, tinyMCEwin, tinyMCEwin_name, \
                             tinyMCEfield, latex_source, math_fontsize, \
                             preview_image_filename, preview_math_srcfile):
        """
        Based off of handleTinyMCEimageChoice(), 
        handleTinyMCEmath() is similar in that it places a .gif math image 
        (and a corresponding .tex LaTeX source file) into the previews dir.
        Rather than copying the image from a user-selected directory, though,
        this routine actually generates the math image using mimetex.
        """
        server_filename = ""
        callback_errors = ""
        errors = 0

        webDir     = Path(G.application.tempWebDir)
        previewDir  = webDir.joinpath('previews')

        if not previewDir.exists():
            log.debug("image previews directory does not yet exist; " \
                    + "creating as %s " % previewDir)
            previewDir.makedirs()
        elif not previewDir.isdir():
            client.alert( \
                _(u'Preview directory %s is a file, cannot replace it') \
                % previewDir)
            log.error("Couldn't preview tinyMCE-chosen image: "+
                      "Preview dir %s is a file, cannot replace it" \
                      % previewDir)
            callback_errors =  "Preview dir is a file, cannot replace"
            errors += 1

        #if errors == 0:
        #    localImagePath = Path(local_filename)
        #    if not localImagePath.exists() or not localImagePath.isfile():
        #        client.alert( \
        #             _(u'Image file %s is not found, cannot preview it') \
        #             % localImagePath)
        #        log.error("Couldn't find tinyMCE-chosen image: %s" \
        #                % localImagePath)
        #        callback_errors = "Image file %s not found, cannot preview" \
        #                % localImagePath
        #        errors += 1

        # the mimetex usage code was swiped from the Math iDevice:
        if latex_source <> "":

            # first write the latex_source out into the preview_math_srcfile,
            # such that it can then be passed into the compile command:
            math_filename = previewDir.joinpath(preview_math_srcfile)
            math_filename_str = math_filename.abspath().encode('utf-8')
            log.info("handleTinyMCEmath: using LaTeX source: " + latex_source)
            log.debug("writing LaTeX source into \'" \
                    + math_filename_str + "\'.")
            math_file = open(math_filename, 'wb')
            # do we need to append a \n here?:
            math_file.write(latex_source)
            math_file.flush()
            math_file.close()


            try: 
                use_latex_sourcefile = math_filename_str
                tempFileName = compile(use_latex_sourcefile, math_fontsize, \
                        latex_is_file=True)
            except Exception, e:
                client.alert(_('MimeTeX compile failed!\n%s' % str(e)))
                log.error("handleTinyMCEmath unable to compile LaTeX using "\
                    +"mimetex, error = " + str(e))
                raise

            # copy the file into previews
            server_filename = previewDir.joinpath(preview_image_filename);
            log.debug("handleTinyMCEmath copying math image from \'"\
                    + tempFileName + "\' to \'" \
                    + server_filename.abspath().encode('utf-8') + "\'.");
            shutil.copyfile(tempFileName, \
                    server_filename.abspath().encode('utf-8'));

            # Delete the temp file made by compile 
            Path(tempFileName).remove()
Beispiel #37
0
    def export(self, package):
        """ 
        Export SCORM package
        """
        # First do the export to a temporary directory
        outputDir = TempDirPath()

        self.metadataType = package.exportMetadataType

        # copy the package's resource files
        package.resourceDir.copyfiles(outputDir)

        # copy the package's resource files, only non existant in outputDir
        #        outputDirFiles = outputDir.files()
        #        for rfile in package.resourceDir.files():
        #            if rfile not in outputDirFiles:
        #                rfile.copy(outputDir)

        # copy the package's resource files, only indexed in package.resources
        #        for md5 in package.resources.values():
        #            for resource in md5:
        #                resource.path.copy(outputDir)

        # Export the package content
        # Import the Scorm Page class , if the secure mode is off.  If the style has it's own page class
        # use that, else use the default one.
        if self.styleSecureMode == "0":
            if (self.styleDir / "scormpage.py").exists():
                global ScormPage
                module = imp.load_source("ScormPage", self.styleDir / "scormpage.py")
                ScormPage = module.ScormPage

        self.pages = [ScormPage("index", 1, package.root, scormType=self.scormType, metadataType=self.metadataType)]

        self.generatePages(package.root, 2)
        uniquifyNames(self.pages)

        for page in self.pages:
            page.save(outputDir)
            if not self.hasForum:
                for idevice in page.node.idevices:
                    if hasattr(idevice, "isForum"):
                        if idevice.forum.lms.lms == "moodle":
                            self.hasForum = True
                            break

        # Create the manifest file
        manifest = Manifest(self.config, outputDir, package, self.pages, self.scormType, self.metadataType)
        manifest.save("imsmanifest.xml")
        if self.hasForum:
            manifest.save("discussionforum.xml")

        # Copy the style sheet files to the output dir
        styleFiles = [self.styleDir / ".." / "base.css"]
        styleFiles += [self.styleDir / ".." / "popup_bg.gif"]
        # And with all the files of the style we avoid problems:
        styleFiles += self.styleDir.files("*.*")
        if self.scormType == "commoncartridge":
            for sf in styleFiles[:]:
                if sf.basename() not in manifest.dependencies:
                    styleFiles.remove(sf)
        self.styleDir.copylist(styleFiles, outputDir)

        # Copy the scripts
        dT = common.getExportDocType()
        if dT == "HTML5":
            jsFile = self.scriptsDir / "exe_html5.js"
            jsFile.copyfile(outputDir / "exe_html5.js")

        # jQuery
        my_style = G.application.config.styleStore.getStyle(page.node.package.style)
        if my_style.hasValidConfig:
            if my_style.get_jquery() == True:
                jsFile = self.scriptsDir / "exe_jquery.js"
                jsFile.copyfile(outputDir / "exe_jquery.js")
        else:
            jsFile = self.scriptsDir / "exe_jquery.js"
            jsFile.copyfile(outputDir / "exe_jquery.js")

        if self.scormType == "commoncartridge":
            jsFile = self.scriptsDir / "common.js"
            jsFile.copyfile(outputDir / "common.js")

        if self.scormType == "scorm2004" or self.scormType == "scorm1.2":
            self.scriptsDir.copylist(("SCORM_API_wrapper.js", "SCOFunctions.js", "common.js"), outputDir)
        # about SCHEMAS:
        schemasDir = ""
        if self.scormType == "scorm1.2":
            schemasDir = self.schemasDir / "scorm1.2"
            schemasDir.copylist(
                (
                    "imscp_rootv1p1p2.xsd",
                    "imsmd_rootv1p2p1.xsd",
                    "adlcp_rootv1p2.xsd",
                    "lom.xsd",
                    "lomCustom.xsd",
                    "ims_xml.xsd",
                ),
                outputDir,
            )
        elif self.scormType == "scorm2004":
            schemasDir = self.schemasDir / "scorm2004"
            schemasDir.copylist(
                (
                    "adlcp_v1p3.xsd",
                    "adlnav_v1p3.xsd",
                    "adlseq_v1p3.xsd",
                    "datatypes.dtd",
                    "imscp_v1p1.xsd",
                    "imsssp_v1p0.xsd",
                    "imsss_v1p0.xsd",
                    "imsss_v1p0auxresource.xsd",
                    "imsss_v1p0control.xsd",
                    "imsss_v1p0delivery.xsd",
                    "imsmd_rootv1p2p1.xsd",
                    "imsss_v1p0limit.xsd",
                    "imsss_v1p0objective.xsd",
                    "imsss_v1p0random.xsd",
                    "imsss_v1p0rollup.xsd",
                    "imsss_v1p0seqrule.xsd",
                    "imsss_v1p0util.xsd",
                    "ims_xml.xsd",
                    "lom.xsd",
                    "lomCustom.xsd",
                    "xml.xsd",
                    "XMLSchema.dtd",
                ),
                outputDir,
            )
            try:
                import shutil, errno

                shutil.copytree(schemasDir / "common", outputDir / "common")
                shutil.copytree(schemasDir / "extend", outputDir / "extend")
                shutil.copytree(schemasDir / "unique", outputDir / "unique")
                shutil.copytree(schemasDir / "vocab", outputDir / "vocab")
            except OSError as exc:
                if exc.errno == errno.ENOTDIR:
                    shutil.copy(schemasDir, outputDir)
                else:
                    raise

        # copy players for media idevices.
        hasFlowplayer = False
        hasMagnifier = False
        hasXspfplayer = False
        hasGallery = False
        hasWikipedia = False
        isBreak = False
        hasInstructions = False
        hasMediaelement = False

        for page in self.pages:
            if isBreak:
                break
            for idevice in page.node.idevices:
                if (
                    hasFlowplayer
                    and hasMagnifier
                    and hasXspfplayer
                    and hasGallery
                    and hasWikipedia
                    and hasInstructions
                    and hasMediaelement
                ):
                    isBreak = True
                    break
                if not hasFlowplayer:
                    if "flowPlayer.swf" in idevice.systemResources:
                        hasFlowplayer = True
                if not hasMagnifier:
                    if "mojomagnify.js" in idevice.systemResources:
                        hasMagnifier = True
                if not hasXspfplayer:
                    if "xspf_player.swf" in idevice.systemResources:
                        hasXspfplayer = True
                if not hasGallery:
                    hasGallery = common.ideviceHasGallery(idevice)
                if not hasWikipedia:
                    if "WikipediaIdevice" == idevice.klass:
                        hasWikipedia = True
                if not hasInstructions:
                    if (
                        "TrueFalseIdevice" == idevice.klass
                        or "MultichoiceIdevice" == idevice.klass
                        or "VerdaderofalsofpdIdevice" == idevice.klass
                        or "EleccionmultiplefpdIdevice" == idevice.klass
                    ):
                        hasInstructions = True
                if not hasMediaelement:
                    hasMediaelement = common.ideviceHasMediaelement(idevice)

        if hasFlowplayer:
            videofile = self.templatesDir / "flowPlayer.swf"
            videofile.copyfile(outputDir / "flowPlayer.swf")
            controlsfile = self.templatesDir / "flowplayer.controls.swf"
            controlsfile.copyfile(outputDir / "flowplayer.controls.swf")
        if hasMagnifier:
            videofile = self.templatesDir / "mojomagnify.js"
            videofile.copyfile(outputDir / "mojomagnify.js")
        if hasXspfplayer:
            videofile = self.templatesDir / "xspf_player.swf"
            videofile.copyfile(outputDir / "xspf_player.swf")
        if hasGallery:
            imageGalleryCSS = self.cssDir / "exe_lightbox.css"
            imageGalleryCSS.copyfile(outputDir / "exe_lightbox.css")
            imageGalleryJS = self.scriptsDir / "exe_lightbox.js"
            imageGalleryJS.copyfile(outputDir / "exe_lightbox.js")
            self.imagesDir.copylist(
                (
                    "exe_lightbox_close.png",
                    "exe_lightbox_loading.gif",
                    "exe_lightbox_next.png",
                    "exe_lightbox_prev.png",
                ),
                outputDir,
            )
        if hasWikipedia:
            wikipediaCSS = self.cssDir / "exe_wikipedia.css"
            wikipediaCSS.copyfile(outputDir / "exe_wikipedia.css")
        if hasInstructions:
            common.copyFileIfNotInStyle("panel-amusements.png", self, outputDir)
            common.copyFileIfNotInStyle("stock-stop.png", self, outputDir)
        if hasMediaelement:
            mediaelement = self.scriptsDir / "mediaelement"
            mediaelement.copyfiles(outputDir)
            if dT != "HTML5":
                jsFile = self.scriptsDir / "exe_html5.js"

        if self.scormType == "scorm1.2" or self.scormType == "scorm2004":
            if package.license == "license GFDL":
                # include a copy of the GNU Free Documentation Licence
                (self.templatesDir / "fdl.html").copyfile(outputDir / "fdl.html")

        if hasattr(package, "scowsinglepage") and package.scowsinglepage:
            page = SinglePage("singlepage_index", 1, package.root)
            page.save(outputDir / "singlepage_index.html")
            # Incluide eXe's icon if the Style doesn't have one
            themePath = Path(G.application.config.stylesDir / package.style)
            themeFavicon = themePath.joinpath("favicon.ico")
            if not themeFavicon.exists():
                faviconFile = self.imagesDir / "favicon.ico"
                faviconFile.copyfile(outputDir / "favicon.ico")
        if hasattr(package, "scowwebsite") and package.scowwebsite:
            website = WebsiteExport(self.config, self.styleDir, outputDir, "website_")
            website.export(package)
            (self.styleDir / "nav.css").copyfile(outputDir / "nav.css")
            # Incluide eXe's icon if the Style doesn't have one
            themePath = Path(G.application.config.stylesDir / package.style)
            themeFavicon = themePath.joinpath("favicon.ico")
            if not themeFavicon.exists():
                faviconFile = self.imagesDir / "favicon.ico"
                faviconFile.copyfile(outputDir / "favicon.ico")
        if hasattr(package, "exportSource") and package.exportSource:
            (G.application.config.webDir / "templates" / "content.xsd").copyfile(outputDir / "content.xsd")
            (outputDir / "content.data").write_bytes(encodeObject(package))
            (outputDir / "contentv3.xml").write_bytes(encodeObjectToXML(package))

        # Zip it up!
        self.filename.safeSave(self.doZip, _("EXPORT FAILED!\nLast succesful export is %s."), outputDir)
        # Clean up the temporary dir
        outputDir.rmtree()
Beispiel #38
0
    def export(self, package):
        """
        Export SCORM package
        """
        # First do the export to a temporary directory
        outputDir = TempDirPath()

        self.metadataType = package.exportMetadataType

        # copy the package's resource files
        for resourceFile in package.resourceDir.walkfiles():
            file = package.resourceDir.relpathto(resourceFile)

            if ("/" in file):
                Dir = Path(outputDir / file[:file.rindex("/")])

                if not Dir.exists():
                    Dir.makedirs()

                resourceFile.copy(outputDir / Dir)
            else:
                resourceFile.copy(outputDir)

        # copy the package's resource files, only non existant in outputDir
#        outputDirFiles = outputDir.files()
#        for rfile in package.resourceDir.files():
#            if rfile not in outputDirFiles:
#                rfile.copy(outputDir)

# copy the package's resource files, only indexed in package.resources
#        for md5 in package.resources.values():
#            for resource in md5:
#                resource.path.copy(outputDir)

# Export the package content
# Import the Scorm Page class , if the secure mode is off.  If the style has it's own page class
# use that, else use the default one.
        if self.styleSecureMode == "0":
            if (self.styleDir / "scormpage.py").exists():
                global ScormPage
                module = imp.load_source("ScormPage",
                                         self.styleDir / "scormpage.py")
                ScormPage = module.ScormPage

        self.pages = [
            ScormPage("index",
                      1,
                      package.root,
                      scormType=self.scormType,
                      metadataType=self.metadataType)
        ]

        self.generatePages(package.root, 2)
        uniquifyNames(self.pages)

        for page in self.pages:
            page.save(outputDir, self.pages)
            if not self.hasForum:
                for idevice in page.node.idevices:
                    if hasattr(idevice, "isForum"):
                        if idevice.forum.lms.lms == "moodle":
                            self.hasForum = True
                            break

        # Create the manifest file
        manifest = Manifest(self.config, outputDir, package, self.pages,
                            self.scormType, self.metadataType)
        modifiedMetaData = manifest.save("imsmanifest.xml")

        # Create lang file
        langFile = open(outputDir + '/common_i18n.js', "w")
        langFile.write(common.getJavaScriptStrings(False))
        langFile.close()

        if self.hasForum:
            manifest.save("discussionforum.xml")

        # Copy the style files to the output dir

        styleFiles = [self.styleDir / '..' / 'popup_bg.gif']
        # And with all the files of the style we avoid problems:
        styleFiles += self.styleDir.files("*.*")
        if self.scormType == "commoncartridge":
            for sf in styleFiles[:]:
                if sf.basename() not in manifest.dependencies:
                    styleFiles.remove(sf)
        self.styleDir.copylist(styleFiles, outputDir)

        listCSSFiles = getFilesCSSToMinify('scorm', self.styleDir)
        exportMinFileCSS(listCSSFiles, outputDir)

        # Copy the scripts

        dT = common.getExportDocType()
        if dT == "HTML5":
            #listFiles+=[self.scriptsDir/'exe_html5.js']
            #listOutFiles+=[outputDir/'exe_html5.js']
            jsFile = (self.scriptsDir / 'exe_html5.js')
            jsFile.copyfile(outputDir / 'exe_html5.js')

        # jQuery
        my_style = G.application.config.styleStore.getStyle(
            page.node.package.style)
        if my_style.hasValidConfig():
            if my_style.get_jquery() == True:
                #listFiles+=[self.scriptsDir/'exe_jquery.js']
                #listOutFiles+=[outputDir/'exe_jquery.js']
                jsFile = (self.scriptsDir / 'exe_jquery.js')
                jsFile.copyfile(outputDir / 'exe_jquery.js')
        else:
            #listFiles+=[self.scriptsDir/'exe_jquery.js']
            #listOutFiles+=[outputDir/'exe_jquery.js']
            jsFile = (self.scriptsDir / 'exe_jquery.js')
            jsFile.copyfile(outputDir / 'exe_jquery.js')

        if self.scormType == "commoncartridge" or self.scormType == "scorm2004" or self.scormType == "scorm1.2":
            listFiles = getFilesJSToMinify('scorm', self.scriptsDir)

        exportMinFileJS(listFiles, outputDir)

        if self.scormType == "scorm2004" or self.scormType == "scorm1.2":
            self.scriptsDir.copylist(
                ('SCORM_API_wrapper.js', 'SCOFunctions.js'), outputDir)

        # about SCHEMAS:
        schemasDir = ""
        if self.scormType == "scorm1.2":
            schemasDir = self.schemasDir / "scorm1.2"
            schemasDir.copylist(('imscp_rootv1p1p2.xsd',
                                 'imsmd_rootv1p2p1.xsd', 'adlcp_rootv1p2.xsd',
                                 'lom.xsd', 'lomCustom.xsd', 'ims_xml.xsd'),
                                outputDir)
        elif self.scormType == "scorm2004":
            schemasDir = self.schemasDir / "scorm2004"
            schemasDir.copylist(
                ('adlcp_v1p3.xsd', 'adlnav_v1p3.xsd', 'adlseq_v1p3.xsd',
                 'datatypes.dtd', 'imscp_v1p1.xsd', 'imsssp_v1p0.xsd',
                 'imsss_v1p0.xsd', 'imsss_v1p0auxresource.xsd',
                 'imsss_v1p0control.xsd', 'imsss_v1p0delivery.xsd',
                 'imsmd_rootv1p2p1.xsd', 'imsss_v1p0limit.xsd',
                 'imsss_v1p0objective.xsd', 'imsss_v1p0random.xsd',
                 'imsss_v1p0rollup.xsd', 'imsss_v1p0seqrule.xsd',
                 'imsss_v1p0util.xsd', 'ims_xml.xsd', 'lom.xsd',
                 'lomCustom.xsd', 'xml.xsd', 'XMLSchema.dtd'), outputDir)
            try:
                import shutil, errno
                shutil.copytree(schemasDir / "common", outputDir / "common")
                shutil.copytree(schemasDir / "extend", outputDir / "extend")
                shutil.copytree(schemasDir / "unique", outputDir / "unique")
                shutil.copytree(schemasDir / "vocab", outputDir / "vocab")
            except OSError as exc:
                if exc.errno == errno.ENOTDIR:
                    shutil.copy(schemasDir, outputDir)
                else:
                    raise

        # copy players for media idevices.
        hasFlowplayer = False
        hasMagnifier = False
        hasXspfplayer = False
        hasGallery = False
        hasFX = False
        hasSH = False
        hasGames = False
        hasElpLink = False
        hasWikipedia = False
        isBreak = False
        hasInstructions = False
        hasMediaelement = False
        hasTooltips = False
        hasABCMusic = False
        listIdevicesFiles = []

        for page in self.pages:
            if isBreak:
                break
            for idevice in page.node.idevices:
                if (hasFlowplayer and hasMagnifier and hasXspfplayer
                        and hasGallery and hasFX and hasSH and hasGames
                        and hasElpLink and hasWikipedia and hasInstructions
                        and hasMediaelement and hasTooltips and hasABCMusic):
                    isBreak = True
                    break
                if not hasFlowplayer:
                    if 'flowPlayer.swf' in idevice.systemResources:
                        hasFlowplayer = True
                if not hasMagnifier:
                    if 'mojomagnify.js' in idevice.systemResources:
                        hasMagnifier = True
                if not hasXspfplayer:
                    if 'xspf_player.swf' in idevice.systemResources:
                        hasXspfplayer = True
                if not hasGallery:
                    hasGallery = common.ideviceHasGallery(idevice)
                if not hasFX:
                    hasFX = common.ideviceHasFX(idevice)
                if not hasSH:
                    hasSH = common.ideviceHasSH(idevice)
                if not hasGames:
                    hasGames = common.ideviceHasGames(idevice)
                if not hasElpLink:
                    hasElpLink = common.ideviceHasElpLink(idevice, package)
                if not hasWikipedia:
                    if 'WikipediaIdevice' == idevice.klass:
                        hasWikipedia = True
                if not hasInstructions:
                    if 'TrueFalseIdevice' == idevice.klass or 'MultichoiceIdevice' == idevice.klass or 'VerdaderofalsofpdIdevice' == idevice.klass or 'EleccionmultiplefpdIdevice' == idevice.klass:
                        hasInstructions = True
                if not hasMediaelement:
                    hasMediaelement = common.ideviceHasMediaelement(idevice)
                if not hasTooltips:
                    hasTooltips = common.ideviceHasTooltips(idevice)
                if not hasABCMusic:
                    hasABCMusic = common.ideviceHasABCMusic(idevice)
                if hasattr(idevice, "_iDeviceDir"):
                    listIdevicesFiles.append(
                        (idevice.get_jsidevice_dir() / 'export'))

            common.exportJavaScriptIdevicesFiles(page.node.idevices, outputDir)

        if hasFlowplayer:
            videofile = (self.templatesDir / 'flowPlayer.swf')
            videofile.copyfile(outputDir / 'flowPlayer.swf')
            controlsfile = (self.templatesDir / 'flowplayer.controls.swf')
            controlsfile.copyfile(outputDir / 'flowplayer.controls.swf')
        if hasMagnifier:
            videofile = (self.templatesDir / 'mojomagnify.js')
            videofile.copyfile(outputDir / 'mojomagnify.js')
        if hasXspfplayer:
            videofile = (self.templatesDir / 'xspf_player.swf')
            videofile.copyfile(outputDir / 'xspf_player.swf')
        if hasGallery:
            exeLightbox = (self.scriptsDir / 'exe_lightbox')
            exeLightbox.copyfiles(outputDir)
        if hasFX:
            exeEffects = (self.scriptsDir / 'exe_effects')
            exeEffects.copyfiles(outputDir)
        if hasSH:
            exeSH = (self.scriptsDir / 'exe_highlighter')
            exeSH.copyfiles(outputDir)
        if hasGames:
            exeGames = (self.scriptsDir / 'exe_games')
            exeGames.copyfiles(outputDir)
            # Add game js string to common_i18n
            langGameFile = open(outputDir + '/common_i18n.js', "a")
            langGameFile.write(common.getGamesJavaScriptStrings(False))
            langGameFile.close()
        if hasElpLink or package.get_exportElp():
            # Export the elp file
            currentPackagePath = Path(package.filename)
            currentPackagePath.copyfile(outputDir / package.name + '.elp')
        if hasWikipedia:
            wikipediaCSS = (self.cssDir / 'exe_wikipedia.css')
            wikipediaCSS.copyfile(outputDir / 'exe_wikipedia.css')
        if hasInstructions:
            common.copyFileIfNotInStyle('panel-amusements.png', self,
                                        outputDir)
            common.copyFileIfNotInStyle('stock-stop.png', self, outputDir)
        if hasMediaelement:
            mediaelement = (self.scriptsDir / 'mediaelement')
            mediaelement.copyfiles(outputDir)
            if dT != "HTML5":
                jsFile = (self.scriptsDir / 'exe_html5.js')
        if hasTooltips:
            exe_tooltips = (self.scriptsDir / 'exe_tooltips')
            exe_tooltips.copyfiles(outputDir)
        if hasABCMusic:
            pluginScripts = (self.scriptsDir /
                             'tinymce_4/js/tinymce/plugins/abcmusic/export')
            pluginScripts.copyfiles(outputDir)
        ext = ".html"
        if G.application.config.cutFileName == "1":
            ext = ".htm"

        if self.scormType == "scorm1.2" or self.scormType == "scorm2004":
            if package.license == "license GFDL":
                # include a copy of the GNU Free Documentation Licence
                (self.templatesDir / 'fdl' + ext).copyfile(outputDir / 'fdl' +
                                                           ext)

        if hasattr(package, 'scowsinglepage') and package.scowsinglepage:
            page = SinglePage("singlepage_index", 1, package.root)
            page.save(outputDir / "singlepage_index" + ext)
            # Incluide eXe's icon if the Style doesn't have one
            themePath = Path(G.application.config.stylesDir / package.style)
            themeFavicon = themePath.joinpath("favicon.ico")
            if not themeFavicon.exists():
                faviconFile = (self.imagesDir / 'favicon.ico')
                faviconFile.copyfile(outputDir / 'favicon.ico')
        if hasattr(package, 'scowwebsite') and package.scowwebsite:
            website = WebsiteExport(self.config, self.styleDir, outputDir,
                                    "website_")
            website.export(package)
            (self.styleDir / 'nav.css').copyfile(outputDir / 'nav.css')
            # Incluide eXe's icon if the Style doesn't have one
            themePath = Path(G.application.config.stylesDir / package.style)
            themeFavicon = themePath.joinpath("favicon.ico")
            if not themeFavicon.exists():
                faviconFile = (self.imagesDir / 'favicon.ico')
                faviconFile.copyfile(outputDir / 'favicon.ico')
        if hasattr(package, 'exportSource') and package.exportSource:
            (G.application.config.webDir / 'templates' /
             'content.xsd').copyfile(outputDir / 'content.xsd')
            (outputDir / 'content.data').write_bytes(encodeObject(package))
            (outputDir / 'contentv3.xml').write_bytes(
                encodeObjectToXML(package))

        # Zip it up!
        self.filename.safeSave(
            self.doZip, _('EXPORT FAILED!\nLast succesful export is %s.'),
            outputDir)
        # Clean up the temporary dir
        outputDir.rmtree()

        return modifiedMetaData
Beispiel #39
0
def ideviceHeader(e, style, mode):
    dT = getExportDocType()
    lb = "\n"  #Line breaks
    #Default HTML tags:
    articleTag = "div"
    headerTag = "div"
    titleTag = "h2"
    if dT == "HTML5":
        articleTag = "article"
        headerTag = "header"
        titleTag = "h1"

    themePath = Path(G.application.config.stylesDir / style)
    themeXMLFile = themePath.joinpath("config.xml")
    themeHasXML = themeHasConfigXML(style)

    w = ''  # Common wrapper
    o = ''  # Old HTML (themes with no config.xml file)
    h = ''  # New HTML
    w2 = ''
    eEm = ''
    if e.idevice.emphasis > 0:
        w2 = '<div class="iDevice_inner">' + lb
        w2 += '<div class="iDevice_content_wrapper">' + lb
        eEm = ' em_iDevice'

    if mode == "preview" and themeHasXML:
        w += '<' + articleTag + ' class="iDevice_wrapper ' + e.idevice.klass + eEm + '" id="id' + e.id + '">' + lb

    w += u"<div class=\"iDevice emphasis" + unicode(e.idevice.emphasis) + "\" "
    if mode == "preview":
        w += u"ondblclick=\"submitLink('edit', " + e.id + ", 0);\""
    w += ">" + lb

    if e.idevice.emphasis > 0:
        h += '<' + headerTag + ' class="iDevice_header"'
        if e.idevice.icon:
            displayIcon = True
            # The following lines should be replaced by something like:
            '''
            if hasattr(e.idevice, 'originalicon'):
                if e.idevice.icon==e.idevice.originalicon:
                    displayIcon = False
            '''
            k = e.idevice.klass
            i = e.idevice.icon
            if (k == 'ListaIdevice' and i == 'question') or (
                    k == 'CasestudyIdevice' and i == 'casestudy'
            ) or (k == 'GalleryIdevice' and i == 'gallery') or (
                    k == 'ClozeIdevice' and i == 'question'
            ) or (k == 'ReflectionIdevice' and i == 'reflection') or (
                    k == 'QuizTestIdevice' and i == 'question') or (
                        k == 'TrueFalseIdevice' and i == 'question') or (
                            k == 'MultiSelectIdevice'
                            and i == 'question') or (k == 'MultichoiceIdevice'
                                                     and i == 'question'):
                displayIcon = False
            # /end
            iconPath = '/style/' + style + '/icon_' + e.idevice.icon + '.gif'
            if mode == "view":
                iconPath = 'icon_' + e.idevice.icon + '.gif'
            myIcon = themePath.joinpath("icon_" + e.idevice.icon + ".gif")
            if myIcon.exists():
                o += u'<img alt="" class="iDevice_icon" src="' + iconPath + '" />'
            if (e.idevice.icon + "Idevice") != e.idevice.klass:
                if myIcon.exists() and displayIcon:
                    h += ' style="background-image:url(' + iconPath + ')"'
        else:
            log.debug("Idevice %s at node %s has no icon" %
                      (e.idevice._title, e.idevice.parentNode._title))
        t = e.idevice.title
        fullT = u'<' + titleTag + ' class="iDeviceTitle">' + t + '</' + titleTag + '>'
        if (t == ""):
            fullT = u'<span class="iDeviceTitle">&nbsp;</span>'
        o += u"<" + titleTag + " class=\"iDeviceTitle\">" + t + "</" + titleTag + ">"
        h += '>'
        h += fullT
        h += '</' + headerTag + '>' + lb

    if e.idevice.emphasis <= 0:
        h = ""
        o = ""
    if themeHasXML:
        return w + h + w2
    else:
        return w + o + w2
    def handleTinyMCEmath(self, client, tinyMCEwin, tinyMCEwin_name, \
                             tinyMCEfield, latex_source, math_fontsize, \
                             preview_image_filename, preview_math_srcfile):
        """
        Based off of handleTinyMCEimageChoice(), 
        handleTinyMCEmath() is similar in that it places a .gif math image 
        (and a corresponding .tex LaTeX source file) into the previews dir.
        Rather than copying the image from a user-selected directory, though,
        this routine actually generates the math image using mimetex.
        """
        server_filename = ""
        callback_errors = ""
        errors = 0

        webDir = Path(G.application.tempWebDir)
        previewDir = webDir.joinpath('previews')

        if not previewDir.exists():
            log.debug("image previews directory does not yet exist; " \
                    + "creating as %s " % previewDir)
            previewDir.makedirs()
        elif not previewDir.isdir():
            client.alert( \
                _(u'Preview directory %s is a file, cannot replace it') \
                % previewDir)
            log.error("Couldn't preview tinyMCE-chosen image: "+
                      "Preview dir %s is a file, cannot replace it" \
                      % previewDir)
            callback_errors = "Preview dir is a file, cannot replace"
            errors += 1

        #if errors == 0:
        #    localImagePath = Path(local_filename)
        #    if not localImagePath.exists() or not localImagePath.isfile():
        #        client.alert( \
        #             _(u'Image file %s is not found, cannot preview it') \
        #             % localImagePath)
        #        log.error("Couldn't find tinyMCE-chosen image: %s" \
        #                % localImagePath)
        #        callback_errors = "Image file %s not found, cannot preview" \
        #                % localImagePath
        #        errors += 1

        # the mimetex usage code was swiped from the Math iDevice:
        if latex_source <> "":

            # first write the latex_source out into the preview_math_srcfile,
            # such that it can then be passed into the compile command:
            math_filename = previewDir.joinpath(preview_math_srcfile)
            math_filename_str = math_filename.abspath().encode('utf-8')
            log.info("handleTinyMCEmath: using LaTeX source: " + latex_source)
            log.debug("writing LaTeX source into \'" \
                    + math_filename_str + "\'.")
            math_file = open(math_filename, 'wb')
            # do we need to append a \n here?:
            math_file.write(latex_source)
            math_file.flush()
            math_file.close()

            try:
                use_latex_sourcefile = math_filename_str
                tempFileName = compile(use_latex_sourcefile, math_fontsize, \
                        latex_is_file=True)
            except Exception, e:
                client.alert(_('MimeTeX compile failed!\n%s' % str(e)))
                log.error("handleTinyMCEmath unable to compile LaTeX using "\
                    +"mimetex, error = " + str(e))
                raise

            # copy the file into previews
            server_filename = previewDir.joinpath(preview_image_filename)
            log.debug("handleTinyMCEmath copying math image from \'"\
                    + tempFileName + "\' to \'" \
                    + server_filename.abspath().encode('utf-8') + "\'.")
            shutil.copyfile(tempFileName, \
                    server_filename.abspath().encode('utf-8'))

            # Delete the temp file made by compile
            Path(tempFileName).remove()
Beispiel #41
0
    def export(self, package):
        """ 
        Export SCORM package
        """
        # First do the export to a temporary directory
        outputDir = TempDirPath()

        self.metadataType = package.exportMetadataType

        # copy the package's resource files
        package.resourceDir.copyfiles(outputDir)

        # copy the package's resource files, only non existant in outputDir
#        outputDirFiles = outputDir.files()
#        for rfile in package.resourceDir.files():
#            if rfile not in outputDirFiles:
#                rfile.copy(outputDir)

        # copy the package's resource files, only indexed in package.resources
#        for md5 in package.resources.values():
#            for resource in md5:
#                resource.path.copy(outputDir)

        # Export the package content
        # Import the Scorm Page class , if the secure mode is off.  If the style has it's own page class
        # use that, else use the default one.
        if self.styleSecureMode=="0":
            if (self.styleDir/"scormpage.py").exists():
                global ScormPage
                module = imp.load_source("ScormPage",self.styleDir/"scormpage.py")
                ScormPage = module.ScormPage


        self.pages = [ ScormPage("index", 1, package.root,
            scormType=self.scormType, metadataType=self.metadataType) ]

        self.generatePages(package.root, 2)
        uniquifyNames(self.pages)

        for page in self.pages:
            page.save(outputDir)
            if not self.hasForum:
                for idevice in page.node.idevices:
                    if hasattr(idevice, "isForum"):
                        if idevice.forum.lms.lms == "moodle":
                            self.hasForum = True
                            break

        # Create the manifest file
        manifest = Manifest(self.config, outputDir, package, self.pages, self.scormType, self.metadataType)
        manifest.save("imsmanifest.xml")
        if self.hasForum:
            manifest.save("discussionforum.xml")
        
        # Copy the style sheet files to the output dir
        styleFiles  = [self.styleDir/'..'/'base.css']
        styleFiles += [self.styleDir/'..'/'popup_bg.gif']
        # And with all the files of the style we avoid problems:
        styleFiles += self.styleDir.files("*.*")
        if self.scormType == "commoncartridge":
            for sf in styleFiles[:]:
                if sf.basename() not in manifest.dependencies:
                    styleFiles.remove(sf)
        self.styleDir.copylist(styleFiles, outputDir)
        
        # Copy the scripts
        dT = common.getExportDocType()
        if dT == "HTML5":
            jsFile = (self.scriptsDir/'exe_html5.js')
            jsFile.copyfile(outputDir/'exe_html5.js')
            
        # jQuery
        my_style = G.application.config.styleStore.getStyle(page.node.package.style)
        if my_style.hasValidConfig:
            if my_style.get_jquery() == True:
                jsFile = (self.scriptsDir/'exe_jquery.js')
                jsFile.copyfile(outputDir/'exe_jquery.js')
        else:
            jsFile = (self.scriptsDir/'exe_jquery.js')
            jsFile.copyfile(outputDir/'exe_jquery.js')
            
        if self.scormType == "commoncartridge":
            jsFile = (self.scriptsDir/'common.js')
            jsFile.copyfile(outputDir/'common.js')

        if self.scormType == "scorm2004" or self.scormType == "scorm1.2":
            self.scriptsDir.copylist(('SCORM_API_wrapper.js',
                                      'SCOFunctions.js', 
                                      'lernmodule_net.js',
                                      'lernmodule_net_custom.js',
                                      'common.js'), outputDir)     
        # about SCHEMAS:
        schemasDir = ""
        if self.scormType == "scorm1.2":
            schemasDir = self.schemasDir/"scorm1.2"
            schemasDir.copylist(('imscp_rootv1p1p2.xsd',
                                'imsmd_rootv1p2p1.xsd',
                                'adlcp_rootv1p2.xsd',
                                'lom.xsd',
                                'lomCustom.xsd',
                                'ims_xml.xsd'), outputDir)
        elif self.scormType == "scorm2004":
            schemasDir = self.schemasDir/"scorm2004"
            schemasDir.copylist(('adlcp_v1p3.xsd',
                                'adlnav_v1p3.xsd',
                                'adlseq_v1p3.xsd', 
                                'datatypes.dtd', 
                                'imscp_v1p1.xsd',
                                'imsssp_v1p0.xsd',
                                'imsss_v1p0.xsd',
                                'imsss_v1p0auxresource.xsd',
                                'imsss_v1p0control.xsd',
                                'imsss_v1p0delivery.xsd',
                                'imsmd_rootv1p2p1.xsd',
                                'imsss_v1p0limit.xsd',
                                'imsss_v1p0objective.xsd',
                                'imsss_v1p0random.xsd',
                                'imsss_v1p0rollup.xsd',
                                'imsss_v1p0seqrule.xsd',
                                'imsss_v1p0util.xsd',
                                'ims_xml.xsd',
                                'lom.xsd',
                                'lomCustom.xsd',
                                'xml.xsd',
                                'XMLSchema.dtd'), outputDir)
            try:
                import shutil, errno
                shutil.copytree(schemasDir/"common", outputDir/"common")
                shutil.copytree(schemasDir/"extend", outputDir/"extend")
                shutil.copytree(schemasDir/"unique", outputDir/"unique")
                shutil.copytree(schemasDir/"vocab", outputDir/"vocab")
            except OSError as exc:
                if exc.errno == errno.ENOTDIR:
                    shutil.copy(schemasDir, outputDir)
                else: raise

        # copy players for media idevices.                
        hasFlowplayer     = False
        hasMagnifier      = False
        hasXspfplayer     = False
        hasGallery        = False
        hasWikipedia      = False
        isBreak           = False
        hasInstructions   = False
        hasMediaelement   = False

        for page in self.pages:
            if isBreak:
                break
            for idevice in page.node.idevices:
                if (hasFlowplayer and hasMagnifier and hasXspfplayer and hasGallery and hasWikipedia and hasInstructions and hasMediaelement):
                    isBreak = True
                    break
                if not hasFlowplayer:
                    if 'flowPlayer.swf' in idevice.systemResources:
                        hasFlowplayer = True
                if not hasMagnifier:
                    if 'mojomagnify.js' in idevice.systemResources:
                        hasMagnifier = True
                if not hasXspfplayer:
                    if 'xspf_player.swf' in idevice.systemResources:
                        hasXspfplayer = True
                if not hasGallery:
                    hasGallery = common.ideviceHasGallery(idevice)
                if not hasWikipedia:
                    if 'WikipediaIdevice' == idevice.klass:
                        hasWikipedia = True
                if not hasInstructions:
                    if 'TrueFalseIdevice' == idevice.klass or 'MultichoiceIdevice' == idevice.klass or 'VerdaderofalsofpdIdevice' == idevice.klass or 'EleccionmultiplefpdIdevice' == idevice.klass:
                        hasInstructions = True
                if not hasMediaelement:
                    hasMediaelement = common.ideviceHasMediaelement(idevice)

        if hasFlowplayer:
            videofile = (self.templatesDir/'flowPlayer.swf')
            videofile.copyfile(outputDir/'flowPlayer.swf')
            controlsfile = (self.templatesDir/'flowplayer.controls.swf')
            controlsfile.copyfile(outputDir/'flowplayer.controls.swf')
        if hasMagnifier:
            videofile = (self.templatesDir/'mojomagnify.js')
            videofile.copyfile(outputDir/'mojomagnify.js')
        if hasXspfplayer:
            videofile = (self.templatesDir/'xspf_player.swf')
            videofile.copyfile(outputDir/'xspf_player.swf')
        if hasGallery:
            imageGalleryCSS = (self.cssDir/'exe_lightbox.css')
            imageGalleryCSS.copyfile(outputDir/'exe_lightbox.css') 
            imageGalleryJS = (self.scriptsDir/'exe_lightbox.js')
            imageGalleryJS.copyfile(outputDir/'exe_lightbox.js') 
            self.imagesDir.copylist(('exe_lightbox_close.png', 'exe_lightbox_loading.gif', 'exe_lightbox_next.png', 'exe_lightbox_prev.png'), outputDir)
        if hasWikipedia:
            wikipediaCSS = (self.cssDir/'exe_wikipedia.css')
            wikipediaCSS.copyfile(outputDir/'exe_wikipedia.css')
        if hasInstructions:
            common.copyFileIfNotInStyle('panel-amusements.png', self, outputDir)
            common.copyFileIfNotInStyle('stock-stop.png', self, outputDir)
        if hasMediaelement:
            mediaelement = (self.scriptsDir/'mediaelement')
            mediaelement.copyfiles(outputDir)
            if dT != "HTML5":
                jsFile = (self.scriptsDir/'exe_html5.js')

        if self.scormType == "scorm1.2" or self.scormType == "scorm2004":
            if package.license == "license GFDL":
                # include a copy of the GNU Free Documentation Licence
                (self.templatesDir/'fdl.html').copyfile(outputDir/'fdl.html')
        
        if hasattr(package, 'scowsinglepage') and package.scowsinglepage:
            page = SinglePage("singlepage_index", 1, package.root)
            page.save(outputDir/"singlepage_index.html")
            # Incluide eXe's icon if the Style doesn't have one
            themePath = Path(G.application.config.stylesDir/package.style)
            themeFavicon = themePath.joinpath("favicon.ico")
            if not themeFavicon.exists():
                faviconFile = (self.imagesDir/'favicon.ico')
                faviconFile.copyfile(outputDir/'favicon.ico')
        if hasattr(package, 'scowwebsite') and package.scowwebsite:
            website = WebsiteExport(self.config, self.styleDir, outputDir, "website_")
            website.export(package)
            (self.styleDir/'nav.css').copyfile(outputDir/'nav.css')
            # Incluide eXe's icon if the Style doesn't have one
            themePath = Path(G.application.config.stylesDir/package.style)
            themeFavicon = themePath.joinpath("favicon.ico")
            if not themeFavicon.exists():
                faviconFile = (self.imagesDir/'favicon.ico')
                faviconFile.copyfile(outputDir/'favicon.ico')
        if hasattr(package, 'exportSource') and package.exportSource:
            (G.application.config.webDir/'templates'/'content.xsd').copyfile(outputDir/'content.xsd')
            (outputDir/'content.data').write_bytes(encodeObject(package))
            (outputDir/'contentv3.xml').write_bytes(encodeObjectToXML(package))

        # Zip it up!
        self.filename.safeSave(self.doZip, _('EXPORT FAILED!\nLast succesful export is %s.'), outputDir)
        # Clean up the temporary dir
        outputDir.rmtree()
Beispiel #42
0
    def copyFiles(self, package, outputDir):
        """
        Copy all the files used by the website.
        """
       
        if os.path.isdir(self.stylesDir):
            # Copy the style sheet files to the output dir
            styleFiles  = [self.stylesDir/'..'/'base.css']
            styleFiles += [self.stylesDir/'..'/'popup_bg.gif']
            styleFiles += self.stylesDir.files("*.css")
            styleFiles += self.stylesDir.files("*.jpg")
            styleFiles += self.stylesDir.files("*.gif")
            styleFiles += self.stylesDir.files("*.png")
            styleFiles += self.stylesDir.files("*.js")
            styleFiles += self.stylesDir.files("*.html")
            styleFiles += self.stylesDir.files("*.ico")
            styleFiles += self.stylesDir.files("*.ttf")
            styleFiles += self.stylesDir.files("*.eot")
            styleFiles += self.stylesDir.files("*.otf")
            styleFiles += self.stylesDir.files("*.woff")
            self.stylesDir.copylist(styleFiles, outputDir)

        # copy the package's resource files
        package.resourceDir.copyfiles(outputDir)
            
        # copy script files.
        my_style = G.application.config.styleStore.getStyle(package.style)
        # jQuery
        if my_style.hasValidConfig:
            if my_style.get_jquery() == True:
                jsFile = (self.scriptsDir/'exe_jquery.js')
                jsFile.copyfile(outputDir/'exe_jquery.js')
        else:
            jsFile = (self.scriptsDir/'exe_jquery.js')
            jsFile.copyfile(outputDir/'exe_jquery.js')
            
        jsFile = (self.scriptsDir/'common.js')
        jsFile.copyfile(outputDir/'common.js')
        #dT = common.getExportDocType()
        dT=common.getExportDocType();
        if dT == "HTML5":
            jsFile = (self.scriptsDir/'exe_html5.js')
            jsFile.copyfile(outputDir/'exe_html5.js')

        # Incluide eXe's icon if the Style doesn't have one
        themePath = Path(G.application.config.stylesDir/package.style)
        themeFavicon = themePath.joinpath("favicon.ico")
        if not themeFavicon.exists():
            faviconFile = (self.imagesDir/'favicon.ico')
            faviconFile.copyfile(outputDir/'favicon.ico')
        
        # copy players for media idevices.                
        hasFlowplayer     = False
        hasMagnifier      = False
        hasXspfplayer     = False
        hasGallery        = False
        hasFX             = False
        hasSH             = False
        hasGames          = False
        hasWikipedia      = False
        isBreak           = False
        hasInstructions   = False
        hasMediaelement   = False
        hasTooltips       = False
        
        for page in self.pages:
            if isBreak:
                break
            for idevice in page.node.idevices:
                if (hasFlowplayer and hasMagnifier and hasXspfplayer and hasGallery and hasFX and hasSH and hasGames and hasWikipedia and hasInstructions and hasMediaelement and hasTooltips):
                    isBreak = True
                    break
                if not hasFlowplayer:
                    if 'flowPlayer.swf' in idevice.systemResources:
                        hasFlowplayer = True
                if not hasMagnifier:
                    if 'mojomagnify.js' in idevice.systemResources:
                        hasMagnifier = True
                if not hasXspfplayer:
                    if 'xspf_player.swf' in idevice.systemResources:
                        hasXspfplayer = True
                if not hasGallery:
                    hasGallery = common.ideviceHasGallery(idevice)
                if not hasFX:
                    hasFX = common.ideviceHasFX(idevice)
                if not hasSH:
                    hasSH = common.ideviceHasSH(idevice)
                if not hasGames:
                    hasGames = common.ideviceHasGames(idevice)
                if not hasWikipedia:
                    if 'WikipediaIdevice' == idevice.klass:
                        hasWikipedia = True
                if not hasInstructions:
                    if 'TrueFalseIdevice' == idevice.klass or 'MultichoiceIdevice' == idevice.klass or 'VerdaderofalsofpdIdevice' == idevice.klass or 'EleccionmultiplefpdIdevice' == idevice.klass:
                        hasInstructions = True
                if not hasMediaelement:
                    hasMediaelement = common.ideviceHasMediaelement(idevice)
                if not hasTooltips:
                    hasTooltips = common.ideviceHasTooltips(idevice)

        if hasFlowplayer:
            videofile = (self.templatesDir/'flowPlayer.swf')
            videofile.copyfile(outputDir/'flowPlayer.swf')
            controlsfile = (self.templatesDir/'flowplayer.controls.swf')
            controlsfile.copyfile(outputDir/'flowplayer.controls.swf')
        if hasMagnifier:
            videofile = (self.templatesDir/'mojomagnify.js')
            videofile.copyfile(outputDir/'mojomagnify.js')
        if hasXspfplayer:
            videofile = (self.templatesDir/'xspf_player.swf')
            videofile.copyfile(outputDir/'xspf_player.swf')
        if hasGallery:
            exeLightbox = (self.scriptsDir/'exe_lightbox')
            exeLightbox.copyfiles(outputDir)
        if hasFX:
            exeEffects = (self.scriptsDir/'exe_effects')
            exeEffects.copyfiles(outputDir)
        if hasSH:
            exeSH = (self.scriptsDir/'exe_highlighter')
            exeSH.copyfiles(outputDir)
        if hasGames:
            exeGames = (self.scriptsDir/'exe_games')
            exeGames.copyfiles(outputDir)
        if hasWikipedia:
            wikipediaCSS = (self.cssDir/'exe_wikipedia.css')
            wikipediaCSS.copyfile(outputDir/'exe_wikipedia.css')
        if hasInstructions:
            common.copyFileIfNotInStyle('panel-amusements.png', self, outputDir)
            common.copyFileIfNotInStyle('stock-stop.png', self, outputDir)
        if hasMediaelement:
            mediaelement = (self.scriptsDir/'mediaelement')
            mediaelement.copyfiles(outputDir)
            dT = common.getExportDocType()
            if dT != "HTML5":
                jsFile = (self.scriptsDir/'exe_html5.js')
                jsFile.copyfile(outputDir/'exe_html5.js')
        if hasTooltips:
            exe_tooltips = (self.scriptsDir/'exe_tooltips')
            exe_tooltips.copyfiles(outputDir)

        if hasattr(package, 'exportSource') and package.exportSource:
            (G.application.config.webDir/'templates'/'content.xsd').copyfile(outputDir/'content.xsd')
            (outputDir/'content.data').write_bytes(encodeObject(package))
            (outputDir/'contentv3.xml').write_bytes(encodeObjectToXML(package))

        if package.license == "license GFDL":
            # include a copy of the GNU Free Documentation Licence
            (self.templatesDir/'fdl.html').copyfile(outputDir/'fdl.html')
Beispiel #43
0
    def convertToFreeText(self):
        """
        Actually do the Converting of 
              MathsIdevice -> FreeTextIdevice,
        now that FreeText can hold embeddded images.
        """
        new_content = ""

        # ensure that an image resource still exists on this ImageWithText,
        # before trying to add it into the FreeText idevice.
        # Why?  corrupt packages have been seen missing resources...
        # (usually in with extra package objects as well, probably
        # from old code doing faulty Extracts, or somesuch nonesense)
        imageResource_exists = False

        if not self.content.gifResource is None:
            if os.path.exists(self.content.gifResource.path) and \
            os.path.isfile(self.content.gifResource.path): 
                imageResource_exists = True
            else:
                log.warn("Couldn't find Maths image when upgrading "\
                        + self.content.gifResource.storageName)

        if imageResource_exists:
            new_content += "<img src=\"resources/" \
                    + self.content.gifResource.storageName + "\" " 
            # create the expected math resource url for comparison later,
            # once we do actually create it:
            math_resource_url="resources/" \
                    + self.content.gifResource.storageName + ".tex\" " 
            new_content += "exe_math_latex=\"" + math_resource_url + "\" "
            new_content += "exe_math_size=\"" + repr(self.content.fontsize) \
                    + "\" "
            # no height or width for math images, eh? nope.
            new_content += "/> \n"

        elif self.content.gifResource:
            new_content += "<BR>\n[WARNING: missing image: " \
                    + self.content.gifResource.storageName + "]\n"


        replacementIdev = FreeTextIdevice(new_content)


        ###########
        # now, copy that content field's content into its _w_resourcePaths,
        # and properly remove the resource directory via Massage....
        # for its _wo_resourcePaths:
        # note that replacementIdev's content field's content 
        # is automatically set at its constructor (above),
        # as is the default content_w_resourcePaths (a copy of content)
        # AND the default content_wo_resourcePaths (a copy of content),
        # so only need to update the content_wo_resourcePaths:
        replacementIdev.content.content_wo_resourcePaths = \
                replacementIdev.content.MassageContentForRenderView( \
                    replacementIdev.content.content_w_resourcePaths)
        # Design note: ahhhhh, the above is a good looking reason to possibly
        # have the MassageContentForRenderView() method
        # just assume its content_w_resourcePaths as the input
        # and write the output to its content_wo_resourcePaths.....
        #######
        
        # next step, add the new IDevice into the same node as this one
        self.parentNode.addIdevice(replacementIdev)
        
        # in passing GalleryImage into the FieldWithResources, 
        # that content field needs to be sure to have an updated 
        # parentNode, courtesy of its idevice: 
        replacementIdev.content.setParentNode()

        # and semi-manually add/create the current image
        # resource into the FreeTextIdevice's TextAreaField, content.
        # the content text will have already been taken care of above,
        # including the ideal <img src=...> including resources path,
        # but still need the actual image resource:
        
        if imageResource_exists:
            # Not sure why this can't be imported up top, but it gives 
            # ImportError: cannot import name GalleryImages, 
            # so here it be: 
            from exe.engine.galleryidevice  import GalleryImage 
            
            full_image_path = self.content.gifResource.path
            # with empty caption:
            new_GalleryImage = GalleryImage(replacementIdev.content, \
                    '',  full_image_path, mkThumbnail=False)

            # and....  write the latex_source out into the preview_math_srcfile
            # such that it can then be passed into the compile command.
            # Using the desired name (image.gif.tex), write it into tempWebDir:
            webDir = Path(G.application.tempWebDir)
            source_tex_name = self.content.gifResource.storageName+".tex"
            math_path = webDir.joinpath(source_tex_name)
            math_filename_str = math_path.abspath().encode('utf-8')

            log.debug("convertToFreeText: writing LaTeX source into \'" \
                                        + math_filename_str + "\'.")
            math_file = open(math_filename_str, 'wb')
            # do we need to append a \n here?:
            math_file.write(self.content.latex)
            math_file.flush()
            math_file.close()

            # finally, creating a resource for the latex_source as well:
            new_GalleryLatex = GalleryImage(replacementIdev.content, \
                    '', math_filename_str, mkThumbnail=False) 
            new_GalleryLatexResource = new_GalleryLatex._imageResource
            mathsrc_resource_path = new_GalleryLatexResource._storageName
            # and re-concatenate from the global resources name, 
            # to build the webUrl to the resource: 
            mathsrc_resource_url = new_GalleryLatex.resourcesUrl \
                    + mathsrc_resource_path
                
            # AND compare with the newly built resource_url from above,
            # to ensure that we've got what we had expected, jah!
            if (mathsrc_resource_url != math_resource_url): 
                log.warn('The math source was resource-ified differently ' \
                        + 'than expected, to: ' + mathsrc_resource_url \
                        + '; the source will need to be recreated.') 
                # right. we COULD go ahead and change the exe_math_latex
                # attribute to point to the actual mathsrc_resource_url,
                # EXCEPT that the entire exemath plugin is currently built
                # with the idea that the source .tex file will always be named
                # as the mathimage.gif.tex, and this exe_math_latex tag
                # is really just letting the rest of the world know that 
                # there IS corresponding source expected there.
                # If exemath is to ever change and use the actual contents
                # of this exe_math_latex tag (rather than just appended .tex),
                # then this could be revisited here.

            else: 
                log.debug('math source was resource-ified properly to: ' \
                        + mathsrc_resource_url)


        # and move the new idevice up to the position following this node!
        while ( self.parentNode.idevices.index(replacementIdev) \
                > ( (self.parentNode.idevices.index(self) + 1))):
            replacementIdev.movePrev()

        # finally: delete THIS idevice itself, deleting it from the node
        self.delete()