Update test coverage

This commit is contained in:
Veronica Berglyd Olsen
2024-10-30 00:08:31 +01:00
parent 3749c9f21d
commit 3d935e29eb
13 changed files with 206 additions and 97 deletions
-1
View File
@@ -903,7 +903,6 @@ class ToDocX(Tokenizer):
"""Populate document.xml."""
rId = self._nextRelId()
xRoot = xmlElement(_wTag("document"))
xRoot.set("xmlns:w14", "http://schemas.microsoft.com/office/word/2010/wordml")
xBody = xmlSubElem(xRoot, _wTag("body"))
self._rels["document.xml"] = DocXXmlRel(
rId=rId,
+2 -6
View File
@@ -2065,12 +2065,8 @@ class GuiDocEditor(QPlainTextEdit):
feature for French, Spanish, etc, so it doesn't insert a
space before colons in meta data lines. See issue #1090.
"""
if char == ":" and len(text) > 1:
if text[0] == "@":
return False
if text[0] == "%":
if text[1:].lstrip()[:9].lower() == "synopsis:":
return False
if char == ":" and len(text) > 1 and text[0] == "@":
return False
return True
def _autoSelect(self) -> QTextCursor:
@@ -1,13 +1,13 @@
<?xml version='1.0' encoding='utf-8'?>
<office:document xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:fo="urn:oasis:names:tc:opendocument:xmlns:xsl-fo-compatible:1.0" xmlns:loext="urn:org:documentfoundation:names:experimental:office:xmlns:loext:1.0" xmlns:meta="urn:oasis:names:tc:opendocument:xmlns:meta:1.0" xmlns:number="urn:oasis:names:tc:opendocument:xmlns:datastyle:1.0" xmlns:office="urn:oasis:names:tc:opendocument:xmlns:office:1.0" xmlns:style="urn:oasis:names:tc:opendocument:xmlns:style:1.0" xmlns:text="urn:oasis:names:tc:opendocument:xmlns:text:1.0" office:version="1.3" office:mimetype="application/vnd.oasis.opendocument.text">
<office:document xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:fo="urn:oasis:names:tc:opendocument:xmlns:xsl-fo-compatible:1.0" xmlns:loext="urn:org:documentfoundation:names:experimental:office:xmlns:loext:1.0" xmlns:meta="urn:oasis:names:tc:opendocument:xmlns:meta:1.0" xmlns:number="urn:oasis:names:tc:opendocument:xmlns:datastyle:1.0" xmlns:office="urn:oasis:names:tc:opendocument:xmlns:office:1.0" xmlns:style="urn:oasis:names:tc:opendocument:xmlns:style:1.0" xmlns:text="urn:oasis:names:tc:opendocument:xmlns:text:1.0" xmlns:xlink="http://www.w3.org/1999/xlink" office:version="1.3" office:mimetype="application/vnd.oasis.opendocument.text">
<office:meta>
<meta:creation-date>2024-10-29T09:33:22</meta:creation-date>
<meta:creation-date>2024-10-29T23:24:19</meta:creation-date>
<meta:generator>novelWriter/2.6a3</meta:generator>
<meta:initial-creator>Jane Smith</meta:initial-creator>
<meta:editing-cycles>1234</meta:editing-cycles>
<meta:editing-duration>P42DT12H34M56S</meta:editing-duration>
<dc:title>Test Project</dc:title>
<dc:date>2024-10-29T09:33:22</dc:date>
<dc:date>2024-10-29T23:24:19</dc:date>
<dc:creator>Jane Smith</dc:creator>
</office:meta>
<office:font-face-decls>
@@ -82,6 +82,12 @@
<style:style style:name="P1" style:family="paragraph" style:parent-style-name="Heading_20_2">
<style:paragraph-properties fo:break-before="page" />
</style:style>
<style:style style:name="T1" style:family="text">
<style:text-properties fo:font-weight="bold" />
</style:style>
<style:style style:name="T2" style:family="text">
<style:text-properties fo:color="#4271ae" style:text-underline-style="solid" style:text-underline-width="auto" style:text-underline-color="font-color" />
</style:style>
</office:automatic-styles>
<office:master-styles>
<style:master-page style:name="Standard" style:page-layout-name="PM1">
@@ -95,10 +101,30 @@
</office:master-styles>
<office:body>
<office:text>
<text:h text:style-name="Heading_20_2" text:outline-level="2">Chapter One</text:h>
<text:p text:style-name="Text_20_body">Text</text:p>
<text:user-field-decls>
<text:user-field-decl office:value-type="float" office:value="3" text:name="ManuscriptTitleCount" />
<text:user-field-decl office:value-type="float" office:value="3" text:name="ManuscriptParagraphCount" />
<text:user-field-decl office:value-type="float" office:value="217" text:name="ManuscriptAllWords" />
<text:user-field-decl office:value-type="float" office:value="211" text:name="ManuscriptTextWords" />
<text:user-field-decl office:value-type="float" office:value="6" text:name="ManuscriptTitleWords" />
<text:user-field-decl office:value-type="float" office:value="1471" text:name="ManuscriptAllChars" />
<text:user-field-decl office:value-type="float" office:value="1441" text:name="ManuscriptTextChars" />
<text:user-field-decl office:value-type="float" office:value="30" text:name="ManuscriptTitleChars" />
<text:user-field-decl office:value-type="float" office:value="1258" text:name="ManuscriptAllWordChars" />
<text:user-field-decl office:value-type="float" office:value="1231" text:name="ManuscriptTextWordChars" />
<text:user-field-decl office:value-type="float" office:value="27" text:name="ManuscriptTitleWordChars" />
</text:user-field-decls>
<text:p text:style-name="Title">My Novel</text:p>
<text:p text:style-name="Text_20_body"><text:span text:style-name="T1">Word Count: </text:span><text:span text:style-name="T1"><text:user-field-get style:data-style-name="N0" text:name="ManuscriptAllWords">0</text:user-field-get></text:span><text:line-break /><text:user-field-get style:data-style-name="N0" text:name="ManuscriptParagraphCount">0</text:user-field-get> paragrphs<text:line-break />Web: <text:a xlink:type="simple" xlink:href="http://example.com" text:style-name="T2">http://example.com</text:a></text:p>
<text:h text:style-name="P1" text:outline-level="2">Chapter One</text:h>
<text:p text:style-name="Text_20_body">Lorem ipsum dolor sit amet, consectetur adipiscing elit. Nunc maximus justo non dictum commodo. Curabitur lacinia tempor orci vel luctus. Phasellus porta metus eu massa luctus, eget euismod risus rhoncus. Vestibulum sed arcu nisi. Maecenas pretium facilisis velit, vel semper lacus aliquam sit amet. Vestibulum vulputate neque ligula, rhoncus blandit turpis consequat id. Mauris sagittis vehicula imperdiet. Duis sed nunc pretium, ornare purus vel, sodales augue. Maecenas a suscipit risus. Quisque volutpat justo eleifend est ullamcorper fermentum. Donec ullamcorper et tortor a laoreet. Nam id risus nisi. Vivamus non imperdiet erat, sit amet imperdiet felis. Mauris vitae neque et est aliquam scelerisque non non ipsum.</text:p>
<text:h text:style-name="P1" text:outline-level="2">Chapter Two</text:h>
<text:p text:style-name="Text_20_body">Text</text:p>
<text:p text:style-name="Text_20_body">Nullam laoreet lorem nec malesuada vehicula. Vivamus tempus sodales lectus sed viverra. Aenean lacinia sollicitudin quam, quis tempus eros suscipit id. Duis sed rutrum nisi, ut pulvinar magna. Nam et cursus tortor. Phasellus ac odio tellus. Nullam in iaculis ipsum. Vivamus ante sem, ultricies sed varius quis, tristique nec tellus. Nullam eu urna vitae lacus hendrerit gravida. Quisque pulvinar erat ex, id efficitur velit sodales vitae. Proin vestibulum, sapien eget mattis euismod, tortor quam viverra risus, at congue mauris tortor eu nunc. Mauris pellentesque elit leo, quis eleifend sem placerat a. Vivamus iaculis dui eget tellus volutpat, ac varius nisi facilisis.<text:note text:id="ftn1" text:note-class="footnote">
<text:note-citation>1</text:note-citation>
<text:note-body>
<text:p text:style-name="Footnote">Lorem ipsum</text:p>
</text:note-body>
</text:note></text:p>
</office:text>
</office:body>
</office:document>
+38 -4
View File
@@ -1,5 +1,5 @@
<?xml version='1.0' encoding='utf-8'?>
<office:document-content xmlns:fo="urn:oasis:names:tc:opendocument:xmlns:xsl-fo-compatible:1.0" xmlns:office="urn:oasis:names:tc:opendocument:xmlns:office:1.0" xmlns:style="urn:oasis:names:tc:opendocument:xmlns:style:1.0" xmlns:text="urn:oasis:names:tc:opendocument:xmlns:text:1.0" office:version="1.3">
<office:document-content xmlns:fo="urn:oasis:names:tc:opendocument:xmlns:xsl-fo-compatible:1.0" xmlns:office="urn:oasis:names:tc:opendocument:xmlns:office:1.0" xmlns:style="urn:oasis:names:tc:opendocument:xmlns:style:1.0" xmlns:text="urn:oasis:names:tc:opendocument:xmlns:text:1.0" xmlns:xlink="http://www.w3.org/1999/xlink" office:version="1.3">
<office:font-face-decls>
<style:font-face style:name="Liberation Serif" style:font-pitch="variable" />
</office:font-face-decls>
@@ -7,13 +7,47 @@
<style:style style:name="P1" style:family="paragraph" style:parent-style-name="Heading_20_2">
<style:paragraph-properties fo:break-before="page" />
</style:style>
<style:style style:name="T1" style:family="text">
<style:text-properties fo:font-weight="bold" />
</style:style>
<style:style style:name="T2" style:family="text">
<style:text-properties fo:color="#4271ae" style:text-underline-style="solid" style:text-underline-width="auto" style:text-underline-color="font-color" />
</style:style>
</office:automatic-styles>
<office:body>
<office:text>
<text:h text:style-name="Heading_20_2" text:outline-level="2">Chapter One</text:h>
<text:p text:style-name="Text_20_body">Text</text:p>
<text:user-field-decls>
<text:user-field-decl office:value-type="float" office:value="3" text:name="ManuscriptTitleCount" />
<text:user-field-decl office:value-type="float" office:value="3" text:name="ManuscriptParagraphCount" />
<text:user-field-decl office:value-type="float" office:value="217" text:name="ManuscriptAllWords" />
<text:user-field-decl office:value-type="float" office:value="211" text:name="ManuscriptTextWords" />
<text:user-field-decl office:value-type="float" office:value="6" text:name="ManuscriptTitleWords" />
<text:user-field-decl office:value-type="float" office:value="1471" text:name="ManuscriptAllChars" />
<text:user-field-decl office:value-type="float" office:value="1441" text:name="ManuscriptTextChars" />
<text:user-field-decl office:value-type="float" office:value="30" text:name="ManuscriptTitleChars" />
<text:user-field-decl office:value-type="float" office:value="1258" text:name="ManuscriptAllWordChars" />
<text:user-field-decl office:value-type="float" office:value="1231" text:name="ManuscriptTextWordChars" />
<text:user-field-decl office:value-type="float" office:value="27" text:name="ManuscriptTitleWordChars" />
</text:user-field-decls>
<text:p text:style-name="Title">My Novel</text:p>
<text:p text:style-name="Text_20_body">
<text:span text:style-name="T1">Word Count: </text:span>
<text:span text:style-name="T1">
<text:user-field-get style:data-style-name="N0" text:name="ManuscriptAllWords">0</text:user-field-get>
</text:span>
<text:line-break />
<text:user-field-get style:data-style-name="N0" text:name="ManuscriptParagraphCount">0</text:user-field-get> paragrphs<text:line-break />Web: <text:a xlink:type="simple" xlink:href="http://example.com" text:style-name="T2">http://example.com</text:a>
</text:p>
<text:h text:style-name="P1" text:outline-level="2">Chapter One</text:h>
<text:p text:style-name="Text_20_body">Lorem ipsum dolor sit amet, consectetur adipiscing elit. Nunc maximus justo non dictum commodo. Curabitur lacinia tempor orci vel luctus. Phasellus porta metus eu massa luctus, eget euismod risus rhoncus. Vestibulum sed arcu nisi. Maecenas pretium facilisis velit, vel semper lacus aliquam sit amet. Vestibulum vulputate neque ligula, rhoncus blandit turpis consequat id. Mauris sagittis vehicula imperdiet. Duis sed nunc pretium, ornare purus vel, sodales augue. Maecenas a suscipit risus. Quisque volutpat justo eleifend est ullamcorper fermentum. Donec ullamcorper et tortor a laoreet. Nam id risus nisi. Vivamus non imperdiet erat, sit amet imperdiet felis. Mauris vitae neque et est aliquam scelerisque non non ipsum.</text:p>
<text:h text:style-name="P1" text:outline-level="2">Chapter Two</text:h>
<text:p text:style-name="Text_20_body">Text</text:p>
<text:p text:style-name="Text_20_body">Nullam laoreet lorem nec malesuada vehicula. Vivamus tempus sodales lectus sed viverra. Aenean lacinia sollicitudin quam, quis tempus eros suscipit id. Duis sed rutrum nisi, ut pulvinar magna. Nam et cursus tortor. Phasellus ac odio tellus. Nullam in iaculis ipsum. Vivamus ante sem, ultricies sed varius quis, tristique nec tellus. Nullam eu urna vitae lacus hendrerit gravida. Quisque pulvinar erat ex, id efficitur velit sodales vitae. Proin vestibulum, sapien eget mattis euismod, tortor quam viverra risus, at congue mauris tortor eu nunc. Mauris pellentesque elit leo, quis eleifend sem placerat a. Vivamus iaculis dui eget tellus volutpat, ac varius nisi facilisis.<text:note text:id="ftn1" text:note-class="footnote">
<text:note-citation>1</text:note-citation>
<text:note-body>
<text:p text:style-name="Footnote">Lorem ipsum</text:p>
</text:note-body>
</text:note>
</text:p>
</office:text>
</office:body>
</office:document-content>
@@ -1,8 +1,8 @@
%%~name: New Scene
%%~path: 000000000000d/000000000000f
%%~kind: NOVEL/DOCUMENT
%%~hash: 0566024662fb6ed7ed645717addd64dabf058915
%%~date: 2024-10-27 13:03:13/2024-10-27 13:03:18
%%~hash: 89b54ddaec2fddfd220e91dd438c84fb3aef9fc2
%%~date: 2024-10-30 00:07:21/2024-10-30 00:07:26
# Novel
## Chapter
@@ -40,7 +40,9 @@ Some “ double quoted text with spaces padded ”.
@object: NoSpaceAdded
% synopsis: No space before this colon.
% synopsis : Space before this is OK.
%Footnote.abc : A simple footnote.
Add space before this colon : See?
@@ -1,6 +1,6 @@
<?xml version='1.0' encoding='utf-8'?>
<novelWriterXML appVersion="2.6a3" hexVersion="0x020600a3" fileVersion="1.5" fileRevision="4" timeStamp="2024-10-27 13:01:24">
<project id="d0f3fe10-c6e6-4310-8bfd-181eb4224eed" saveCount="3" autoCount="2" editTime="6">
<novelWriterXML appVersion="2.6a3" hexVersion="0x020600a3" fileVersion="1.5" fileRevision="4" timeStamp="2024-10-30 00:06:45">
<project id="d0f3fe10-c6e6-4310-8bfd-181eb4224eed" saveCount="3" autoCount="2" editTime="5">
<name>New Project</name>
<author>Jane Doe</author>
</project>
@@ -46,7 +46,7 @@
<name status="s000000" import="i000004" active="yes">New Chapter</name>
</item>
<item handle="000000000000f" parent="000000000000d" root="0000000000008" order="1" type="FILE" class="NOVEL" layout="DOCUMENT">
<meta expanded="no" heading="H1" charCount="918" wordCount="154" paraCount="17" cursorPos="1140" />
<meta expanded="no" heading="H1" charCount="918" wordCount="154" paraCount="17" cursorPos="1174" />
<name status="s000000" import="i000004" active="yes">New Scene</name>
</item>
<item handle="0000000000009" parent="None" root="0000000000009" order="1" type="ROOT" class="PLOT">
+1
View File
@@ -1490,5 +1490,6 @@ def testCoreIndex_processComment():
# Padding with term
assert processComment("%note.term: Hi") == (nwComment.NOTE, "term", "Hi", 6, 11)
assert processComment("% note.term: Hi") == (nwComment.NOTE, "term", "Hi", 7, 12)
assert processComment("% note.term : Hi") == (nwComment.NOTE, "term", "Hi", 7, 13)
assert processComment("% note. term : Hi") == (nwComment.PLAIN, "", "note. term : Hi", 0, 0)
assert processComment("% note . term : Hi") == (nwComment.PLAIN, "", "note . term : Hi", 0, 0)
+45 -21
View File
@@ -32,28 +32,9 @@ from novelwriter.core.docbuild import NWBuildDocument
from novelwriter.core.project import NWProject
from novelwriter.enum import nwBuildFmt
from novelwriter.formats.shared import BlockFmt, BlockTyp
from novelwriter.formats.todocx import ToDocX, _mkTag, _wTag
from novelwriter.formats.todocx import OOXML_SCM, ToDocX, _mkTag, _wTag
from tests.tools import DOCX_IGNORE, cmpFiles
OOXML_SCM = "http://schemas.openxmlformats.org"
XML_NS = [
f' xmlns:r="{OOXML_SCM}/officeDocument/2006/relationships"',
f' xmlns:w="{OOXML_SCM}/wordprocessingml/2006/main"',
f' xmlns:cp="{OOXML_SCM}/package/2006/metadata/core-properties"',
' xmlns:dc="http://purl.org/dc/elements/1.1/"',
' xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"',
' xmlns:xml="http://www.w3.org/XML/1998/namespace"',
' xmlns:dcterms="http://purl.org/dc/terms/"',
]
def xmlToText(xElem):
"""Get the text content of an XML element."""
rTxt = ET.tostring(xElem, encoding="utf-8", xml_declaration=False).decode()
for ns in XML_NS:
rTxt = rTxt.replace(ns, "")
return rTxt
from tests.tools import DOCX_IGNORE, cmpFiles, xmlToText
@pytest.mark.core
@@ -610,6 +591,49 @@ def testFmtToDocX_Footnotes(mockGUI):
)
@pytest.mark.core
def testFmtToDocX_Fields(mockGUI):
"""Test formatting of footnotes."""
project = NWProject()
doc = ToDocX(project)
doc.initDocument()
# Field Builder
xNode = doc._generateField("a:b", 0x00)
assert isinstance(xNode, ET.Element)
assert xmlToText(xNode) == "<w:r><w:rPr /><w:t>0</w:t></w:r>"
assert doc._usedFields == [(xNode.find(_wTag("t")), "b")]
assert doc._generateField("a", 0x00) is None
# Full Processing
doc._text = (
"Word Count: [field:allWords]\n"
"Character Count: [field:allChars]\n"
"Chicken Count: [field:allChickens]\n"
)
doc.tokenizeText()
doc.doConvert()
doc.countStats()
doc._documentXml(None, None)
assert xmlToText(doc._files["document.xml"].xml) == (
'<w:document><w:body><w:p><w:pPr><w:pStyle w:val="Normal" /></w:pPr>'
'<w:r><w:rPr /><w:t xml:space="preserve">Word Count: </w:t></w:r>'
'<w:r><w:rPr /><w:t>6</w:t></w:r>'
'<w:r><w:rPr /><w:br /><w:t xml:space="preserve">Character Count: </w:t></w:r>'
'<w:r><w:rPr /><w:t>46</w:t></w:r>'
'<w:r><w:rPr /><w:br /><w:t xml:space="preserve">Chicken Count: </w:t></w:r>'
'<w:r><w:rPr /><w:t>0</w:t></w:r>'
'</w:p><w:sectPr>'
'<w:footnotePr><w:numFmt w:val="decimal" /></w:footnotePr>'
'<w:pgSz w:w="11905" w:h="16837" w:orient="portrait" />'
'<w:pgMar w:top="1133" w:right="1133" w:bottom="1133" w:left="1133" '
'w:header="566" w:footer="0" w:gutter="0" />'
'<w:pgNumType w:start="1" w:fmt="decimal" /><w:titlePg />'
'</w:sectPr></w:body></w:document>'
)
@pytest.mark.core
def testFmtToDocX_SaveDocument(mockGUI, prjLipsum, fncPath, tstPaths):
"""Test document output."""
+4 -1
View File
@@ -45,7 +45,7 @@ class BareTokenizer(Tokenizer):
super().doConvert() # type: ignore (deliberate check)
def closeDocument(self):
super().doConvert() # type: ignore (deliberate check)
super().closeDocument() # type: ignore (deliberate check)
def saveDocument(self, path) -> None:
super().saveDocument(path) # type: ignore (deliberate check)
@@ -60,6 +60,9 @@ def testFmtToken_Abstracts(mockGUI, tstPaths):
with pytest.raises(NotImplementedError):
tokens.doConvert()
with pytest.raises(NotImplementedError):
tokens.closeDocument()
with pytest.raises(NotImplementedError):
tokens.saveDocument(tstPaths)
+59 -26
View File
@@ -35,26 +35,7 @@ from novelwriter.core.project import NWProject
from novelwriter.formats.shared import BlockFmt, BlockTyp, TextFmt
from novelwriter.formats.toodt import ODTParagraphStyle, ODTTextStyle, ToOdt, XMLParagraph, _mkTag
from tests.tools import ODT_IGNORE, cmpFiles
XML_NS = [
' xmlns:dc="http://purl.org/dc/elements/1.1/"',
' xmlns:fo="urn:oasis:names:tc:opendocument:xmlns:xsl-fo-compatible:1.0"',
' xmlns:loext="urn:org:documentfoundation:names:experimental:office:xmlns:loext:1.0"',
' xmlns:meta="urn:oasis:names:tc:opendocument:xmlns:meta:1.0"',
' xmlns:office="urn:oasis:names:tc:opendocument:xmlns:office:1.0"',
' xmlns:style="urn:oasis:names:tc:opendocument:xmlns:style:1.0"',
' xmlns:text="urn:oasis:names:tc:opendocument:xmlns:text:1.0"',
' xmlns:xlink="http://www.w3.org/1999/xlink"',
]
def xmlToText(xElem):
"""Get the text content of an XML element."""
rTxt = ET.tostring(xElem, encoding="utf-8", xml_declaration=False).decode()
for ns in XML_NS:
rTxt = rTxt.replace(ns, "")
return rTxt
from tests.tools import ODT_IGNORE, cmpFiles, xmlToText
@pytest.mark.core
@@ -237,6 +218,46 @@ def testFmtToOdt_TextFormatting(mockGUI):
)
@pytest.mark.core
def testFmtToOdt_Fields(mockGUI):
"""Test formatting of footnotes."""
project = NWProject()
odt = ToOdt(project, True)
odt.initDocument()
# Field Builder
xNode = odt._generateField("a:allWords", 0x00)
assert isinstance(xNode, ET.Element)
assert xmlToText(xNode) == (
'<text:user-field-getstyle:data-style-name="N0" text:name="ManuscriptAllWords">'
'0</text:user-field-get>'
)
# assert odt._usedFields == [(xNode.find(_wTag("t")), "b")]
assert odt._generateField("a", 0x00) is None
# Full Processing
odt._text = (
"Word Count: [field:allWords]\n"
"Character Count: [field:allChars]\n"
"Chicken Count: [field:allChickens]\n"
)
odt.tokenizeText()
odt.doConvert()
odt.countStats()
assert xmlToText(odt._xBody) == (
'<office:body><office:text>'
'<text:p text:style-name="Text_20_body">'
'Word Count: <text:user-field-get style:data-style-name="N0" '
'text:name="ManuscriptAllWords">0</text:user-field-get><text:line-break />'
'Character Count: <text:user-field-get style:data-style-name="N0" '
'text:name="ManuscriptAllChars">0</text:user-field-get><text:line-break />'
'Chicken Count: <text:user-field-get style:data-style-name="N0" '
'text:name="ManuscriptAllChickens">0</text:user-field-get></text:p>'
'</office:text></office:body>'
)
@pytest.mark.core
def testFmtToOdt_DialogueFormatting(mockGUI):
"""Test formatting of dialogue."""
@@ -770,7 +791,7 @@ def testFmtToOdt_ConvertDirect(mockGUI):
@pytest.mark.core
def testFmtToOdt_SaveFlat(mockGUI, fncPath, tstPaths):
def testFmtToOdt_SaveFlat(mockGUI, fncPath, tstPaths, ipsumText):
"""Test the document save functions."""
project = NWProject()
project.data.setAuthor("Jane Smith")
@@ -796,14 +817,20 @@ def testFmtToOdt_SaveFlat(mockGUI, fncPath, tstPaths):
assert odt._mDocRight == "1.500cm"
odt._text = (
"#! My Novel\n\n"
"**Word Count: [field:allWords]**\n"
"[field:paragraphCount] paragrphs\n"
"Web: http://example.com\n\n"
"## Chapter One\n\n"
"Text\n\n"
f"{ipsumText[0]}\n\n"
"## Chapter Two\n\n"
"Text\n\n"
f"{ipsumText[1]}[footnote:abc]\n\n"
"%Footnote.abc: Lorem ipsum\n\n"
)
odt.tokenizeText()
odt.initDocument()
odt.doConvert()
odt.countStats()
odt.closeDocument()
flatFile = fncPath / "document.fodt"
@@ -818,7 +845,7 @@ def testFmtToOdt_SaveFlat(mockGUI, fncPath, tstPaths):
@pytest.mark.core
def testFmtToOdt_SaveFull(mockGUI, fncPath, tstPaths):
def testFmtToOdt_SaveFull(mockGUI, fncPath, tstPaths, ipsumText):
"""Test the document save functions."""
project = NWProject()
project.data.setAuthor("Jane Smith")
@@ -833,14 +860,20 @@ def testFmtToOdt_SaveFull(mockGUI, fncPath, tstPaths):
odt.setHeaderFormat(f"{nwHeadFmt.DOC_PROJECT} - {nwHeadFmt.DOC_AUTHOR}", 0)
odt._text = (
"#! My Novel\n\n"
"**Word Count: [field:allWords]**\n"
"[field:paragraphCount] paragrphs\n"
"Web: http://example.com\n\n"
"## Chapter One\n\n"
"Text\n\n"
f"{ipsumText[0]}\n\n"
"## Chapter Two\n\n"
"Text\n\n"
f"{ipsumText[1]}[footnote:abc]\n\n"
"%Footnote.abc: Lorem ipsum\n\n"
)
odt.tokenizeText()
odt.initDocument()
odt.doConvert()
odt.countStats()
odt.closeDocument()
fullFile = fncPath / "document.odt"
-24
View File
@@ -2184,27 +2184,3 @@ def testGuiEditor_Search(qtbot, monkeypatch, nwGUI, prjLipsum):
assert docEditor.textCursor().selectedText() == ""
# qtbot.stop()
@pytest.mark.gui
def testGuiEditor_StaticMethods():
"""Test the document editor's static methods."""
# Check the method that decides if it is allowed to insert a space
# before a colon using the French, Spanish, etc language feature
assert GuiDocEditor._allowSpaceBeforeColon("", "") is True
assert GuiDocEditor._allowSpaceBeforeColon("", ":") is True
assert GuiDocEditor._allowSpaceBeforeColon("some text", ":") is True
assert GuiDocEditor._allowSpaceBeforeColon("@:", ":") is False
assert GuiDocEditor._allowSpaceBeforeColon("@>", ">") is True
assert GuiDocEditor._allowSpaceBeforeColon("%", ":") is True
assert GuiDocEditor._allowSpaceBeforeColon("%:", ":") is True
assert GuiDocEditor._allowSpaceBeforeColon("%synopsis:", ":") is False
assert GuiDocEditor._allowSpaceBeforeColon("%Synopsis:", ":") is False
assert GuiDocEditor._allowSpaceBeforeColon("% synopsis:", ":") is False
assert GuiDocEditor._allowSpaceBeforeColon("% Synopsis:", ":") is False
assert GuiDocEditor._allowSpaceBeforeColon("% synopsis:", ":") is False
assert GuiDocEditor._allowSpaceBeforeColon("% Synopsis:", ":") is False
assert GuiDocEditor._allowSpaceBeforeColon("%synopsis :", ":") is True
assert GuiDocEditor._allowSpaceBeforeColon("%Synopsis :", ":") is True
+7 -2
View File
@@ -474,7 +474,7 @@ def testGuiMain_Editing(qtbot, monkeypatch, nwGUI, projPath, tstPaths, mockRnd):
# Special Formatting
# ==================
# Insert spaces before colon, but ignore tags and synopsis
# Insert spaces before colon, but ignore tags
docEditor._typPadBefore = ":"
for c in "@object: NoSpaceAdded":
@@ -482,7 +482,12 @@ def testGuiMain_Editing(qtbot, monkeypatch, nwGUI, projPath, tstPaths, mockRnd):
qtbot.keyClick(docEditor, Qt.Key.Key_Return, delay=KEY_DELAY)
qtbot.keyClick(docEditor, Qt.Key.Key_Return, delay=KEY_DELAY)
for c in "% synopsis: No space before this colon.":
for c in "% synopsis: Space before this is OK.":
qtbot.keyClick(docEditor, c, delay=KEY_DELAY)
qtbot.keyClick(docEditor, Qt.Key.Key_Return, delay=KEY_DELAY)
qtbot.keyClick(docEditor, Qt.Key.Key_Return, delay=KEY_DELAY)
for c in "%Footnote.abc: A simple footnote.":
qtbot.keyClick(docEditor, c, delay=KEY_DELAY)
qtbot.keyClick(docEditor, Qt.Key.Key_Return, delay=KEY_DELAY)
qtbot.keyClick(docEditor, Qt.Key.Key_Return, delay=KEY_DELAY)
+10
View File
@@ -21,6 +21,7 @@ along with this program. If not, see <https://www.gnu.org/licenses/>.
from __future__ import annotations
import shutil
import xml.etree.ElementTree as ET
from datetime import datetime
from pathlib import Path
@@ -110,6 +111,15 @@ def cmpFiles(
return not diffFound
def xmlToText(xElem):
"""Get the text content of an XML element."""
text = ET.tostring(xElem, encoding="utf-8", xml_declaration=False).decode()
bits = text.partition(">")
node = bits[0].partition(" ")
rest = " ".join(x for x in node[2].split() if not x.startswith("xmlns")).replace("/", " /")
return f"{node[0]}{rest}{bits[1]}{bits[2]}"
def readFile(fileName: str | Path):
"""Returns the content of a file as a string."""
with open(fileName, mode="r", encoding="utf-8") as inFile: