def _buildPreview(self): """Build a preview of the project in the document viewer. """ # Get Settings fmtTitle = self.fmtTitle.text().strip() fmtChapter = self.fmtChapter.text().strip() fmtUnnumbered = self.fmtUnnumbered.text().strip() fmtScene = self.fmtScene.text().strip() fmtSection = self.fmtSection.text().strip() justifyText = self.justifyText.isChecked() noStyling = self.noStyling.isChecked() textFont = self.textFont.text() textSize = self.textSize.value() incSynopsis = self.includeSynopsis.isChecked() incComments = self.includeComments.isChecked() incKeywords = self.includeKeywords.isChecked() novelFiles = self.novelFiles.isChecked() noteFiles = self.noteFiles.isChecked() ignoreFlag = self.ignoreFlag.isChecked() includeBody = self.includeBody.isChecked() replaceTabs = self.replaceTabs.isChecked() makeHtml = ToHtml(self.theProject, self.theParent) makeHtml.setTitleFormat(fmtTitle) makeHtml.setChapterFormat(fmtChapter) makeHtml.setUnNumberedFormat(fmtUnnumbered) makeHtml.setSceneFormat(fmtScene, fmtScene == "") makeHtml.setSectionFormat(fmtSection, fmtSection == "") makeHtml.setBodyText(includeBody) makeHtml.setSynopsis(incSynopsis) makeHtml.setComments(incComments) makeHtml.setKeywords(incKeywords) makeHtml.setJustify(justifyText) makeHtml.setStyles(not noStyling) # Make sure the tree order is correct self.theParent.treeView.flushTreeOrder() self.buildProgress.setMaximum(len(self.theProject.projTree)) self.buildProgress.setValue(0) tStart = int(time()) self.htmlText = [] self.htmlStyle = [] self.nwdText = [] htmlSize = 0 for nItt, tItem in enumerate(self.theProject.projTree): noteRoot = noteFiles noteRoot &= tItem.itemType == nwItemType.ROOT noteRoot &= tItem.itemClass != nwItemClass.NOVEL noteRoot &= tItem.itemClass != nwItemClass.ARCHIVE try: if noteRoot: # Add headers for root folders of notes makeHtml.addRootHeading(tItem.itemHandle) makeHtml.doConvert() self.htmlText.append(makeHtml.getResult()) self.nwdText.append(makeHtml.getFilteredMarkdown()) htmlSize += makeHtml.getResultSize() elif self._checkInclude(tItem, noteFiles, novelFiles, ignoreFlag): makeHtml.setText(tItem.itemHandle) makeHtml.doAutoReplace() makeHtml.tokenizeText() makeHtml.doHeaders() makeHtml.doConvert() makeHtml.doPostProcessing() self.htmlText.append(makeHtml.getResult()) self.nwdText.append(makeHtml.getFilteredMarkdown()) htmlSize += makeHtml.getResultSize() except Exception as e: logger.error("Failed to generate html of document '%s'" % tItem.itemHandle) logger.error(str(e)) self.docView.setText( ("Failed to generate preview. " "Document with title '%s' could not be parsed.") % tItem.itemName) return False # Update progress bar, also for skipped items self.buildProgress.setValue(nItt + 1) if makeHtml.errData: self.theParent.makeAlert( ("There were problems when building the project:" "<br>- %s") % "<br>- ".join(makeHtml.errData), nwAlert.ERROR) if replaceTabs: htmlText = [] eightSpace = " " * 8 for aLine in self.htmlText: htmlText.append(aLine.replace("\t", eightSpace)) self.htmlText = htmlText nwdText = [] for aLine in self.nwdText: nwdText.append(aLine.replace("\t", " ")) self.nwdText = nwdText tEnd = int(time()) logger.debug("Built project in %.3f ms" % (1000 * (tEnd - tStart))) self.htmlStyle = makeHtml.getStyleSheet() self.buildTime = tEnd # Load the preview document with the html data self.docView.setTextFont(textFont, textSize) self.docView.setJustify(justifyText) if noStyling: self.docView.clearStyleSheet() else: self.docView.setStyleSheet(self.htmlStyle) if htmlSize < nwConst.maxBuildSize: self.docView.setContent(self.htmlText, self.buildTime) self._enableQtSave(True) else: self.docView.setText( "Failed to generate preview. The result is too big.") self._enableQtSave(False) self._saveCache() return
def testCoreToHtml_Convert(dummyGUI): """Test the converter of the ToHtml class. """ theProject = NWProject(dummyGUI) dummyGUI.theIndex = NWIndex(theProject, dummyGUI) theHtml = ToHtml(theProject, dummyGUI) # Export Mode # =========== theHtml.isNovel = True # Header 1 theHtml.theText = "# Title\n" theHtml.tokenizeText() theHtml.doConvert() assert theHtml.theResult == "<h1 class='title'>Title</h1>\n" # Header 2 theHtml.theText = "## Chapter Title\n" theHtml.tokenizeText() theHtml.doConvert() assert theHtml.theResult == "<h1>Chapter Title</h1>\n" # Header 3 theHtml.theText = "### Scene Title\n" theHtml.tokenizeText() theHtml.doConvert() assert theHtml.theResult == "<h2>Scene Title</h2>\n" # Header 4 theHtml.theText = "#### Section Title\n" theHtml.tokenizeText() theHtml.doConvert() assert theHtml.theResult == "<h3>Section Title</h3>\n" theHtml.isNovel = False theHtml.setLinkHeaders(True) # Header 1 theHtml.theText = "# Heading One\n" theHtml.tokenizeText() theHtml.doConvert() assert theHtml.theResult == "<h1><a name='T000001'></a>Heading One</h1>\n" # Header 2 theHtml.theText = "## Heading Two\n" theHtml.tokenizeText() theHtml.doConvert() assert theHtml.theResult == "<h2><a name='T000001'></a>Heading Two</h2>\n" # Header 3 theHtml.theText = "### Heading Three\n" theHtml.tokenizeText() theHtml.doConvert() assert theHtml.theResult == "<h3><a name='T000001'></a>Heading Three</h3>\n" # Header 4 theHtml.theText = "#### Heading Four\n" theHtml.tokenizeText() theHtml.doConvert() assert theHtml.theResult == "<h4><a name='T000001'></a>Heading Four</h4>\n" # Text theHtml.theText = "Some **nested bold and _italic_ and ~~strikethrough~~ text** here\n" theHtml.tokenizeText() theHtml.doConvert() assert theHtml.theResult == ( "<p>Some <strong>nested bold and <em>italic</em> and " "<del>strikethrough</del> text</strong> here</p>\n") # Text w/Hard Break theHtml.theText = "Line one \nLine two \nLine three\n" theHtml.tokenizeText() theHtml.doConvert() assert theHtml.theResult == ( "<p class='break'>Line one<br/>Line two<br/>Line three</p>\n") # Synopsis theHtml.theText = "%synopsis: The synopsis ...\n" theHtml.tokenizeText() theHtml.doConvert() assert theHtml.theResult == "" theHtml.setSynopsis(True) theHtml.theText = "%synopsis: The synopsis ...\n" theHtml.tokenizeText() theHtml.doConvert() assert theHtml.theResult == ( "<p class='synopsis'><strong>Synopsis:</strong> The synopsis ...</p>\n" ) # Comment theHtml.theText = "% A comment ...\n" theHtml.tokenizeText() theHtml.doConvert() assert theHtml.theResult == "" theHtml.setComments(True) theHtml.theText = "% A comment ...\n" theHtml.tokenizeText() theHtml.doConvert() assert theHtml.theResult == ( "<p class='comment'><strong>Comment:</strong> A comment ...</p>\n") # Keywords theHtml.theText = "@char: Bod, Jane\n" theHtml.tokenizeText() theHtml.doConvert() assert theHtml.theResult == "" theHtml.setKeywords(True) theHtml.theText = "@char: Bod, Jane\n" theHtml.tokenizeText() theHtml.doConvert() assert theHtml.theResult == ( "<p><span class='tags'>Characters:</span> " "<a href='#tag_Bod'>Bod</a>, <a href='#tag_Jane'>Jane</a></p>\n") # Multiple Keywords theHtml.setKeywords(True) theHtml.theText = "## Chapter\n\n@pov: Bod\n@plot: Main\n@location: Europe\n\n" theHtml.tokenizeText() theHtml.doConvert() assert theHtml.theResult == ( "<h2>" "<a name='T000001'></a>Chapter</h2>\n" "<p style='margin-bottom: 0;'>" "<span class='tags'>Point of View:</span> <a href='#tag_Bod'>Bod</a>" "</p>\n" "<p style='margin-bottom: 0; margin-top: 0;'>" "<span class='tags'>Plot:</span> <a href='#tag_Main'>Main</a>" "</p>\n" "<p style='margin-top: 0;'>" "<span class='tags'>Locations:</span> <a href='#tag_Europe'>Europe</a>" "</p>\n") # Direct Tests # ============ theHtml.isNovel = True # Title theHtml.theTokens = [ (theHtml.T_TITLE, 1, "A Title", None, theHtml.A_PBB_AUT | theHtml.A_CENTRE), (theHtml.T_EMPTY, 1, "", None, theHtml.A_NONE), ] theHtml.doConvert() assert theHtml.theResult == ( "<h1 class='title' style='text-align: center; page-break-before: auto;'>" "<a name='T000001'></a>A Title</h1>\n") # Separator theHtml.theTokens = [ (theHtml.T_SEP, 1, "* * *", None, theHtml.A_CENTRE), (theHtml.T_EMPTY, 1, "", None, theHtml.A_NONE), ] theHtml.doConvert() assert theHtml.theResult == "<p class='sep'>* * *</p>\n" # Skip theHtml.theTokens = [ (theHtml.T_SKIP, 1, "", None, theHtml.A_NONE), (theHtml.T_EMPTY, 1, "", None, theHtml.A_NONE), ] theHtml.doConvert() assert theHtml.theResult == "<p class='skip'> </p>\n" # Styles # ====== theHtml.setLinkHeaders(False) # Align Left theHtml.setStyles(False) theHtml.theTokens = [ (theHtml.T_HEAD1, 1, "A Title", None, theHtml.A_LEFT), ] theHtml.doConvert() assert theHtml.theResult == ("<h1 class='title'>A Title</h1>\n") theHtml.setStyles(True) # Align Left theHtml.theTokens = [ (theHtml.T_HEAD1, 1, "A Title", None, theHtml.A_LEFT), ] theHtml.doConvert() assert theHtml.theResult == ( "<h1 class='title' style='text-align: left;'>A Title</h1>\n") # Align Right theHtml.theTokens = [ (theHtml.T_HEAD1, 1, "A Title", None, theHtml.A_RIGHT), ] theHtml.doConvert() assert theHtml.theResult == ( "<h1 class='title' style='text-align: right;'>A Title</h1>\n") # Align Centre theHtml.theTokens = [ (theHtml.T_HEAD1, 1, "A Title", None, theHtml.A_CENTRE), ] theHtml.doConvert() assert theHtml.theResult == ( "<h1 class='title' style='text-align: center;'>A Title</h1>\n") # Align Justify theHtml.theTokens = [ (theHtml.T_HEAD1, 1, "A Title", None, theHtml.A_JUSTIFY), ] theHtml.doConvert() assert theHtml.theResult == ( "<h1 class='title' style='text-align: justify;'>A Title</h1>\n") # Page Break Always theHtml.theTokens = [ (theHtml.T_HEAD1, 1, "A Title", None, theHtml.A_PBB | theHtml.A_PBA), ] theHtml.doConvert() assert theHtml.theResult == ( "<h1 class='title' " "style='page-break-before: always; page-break-after: always;'>A Title</h1>\n" ) # Page Break Auto theHtml.theTokens = [ (theHtml.T_HEAD1, 1, "A Title", None, theHtml.A_PBB_AUT | theHtml.A_PBA_AUT), ] theHtml.doConvert() assert theHtml.theResult == ( "<h1 class='title' " "style='page-break-before: auto; page-break-after: auto;'>A Title</h1>\n" ) # Preview Mode # ============ theHtml.setPreview(True, True) # Text (HTML4) theHtml.theText = "Some **nested bold and _italic_ and ~~strikethrough~~ text** here\n" theHtml.tokenizeText() theHtml.doConvert() assert theHtml.theResult == ( "<p>Some <b>nested bold and <i>italic</i> and " "<span style='text-decoration: line-through;'>strikethrough</span> " "text</b> here</p>\n")