Add "short description" feature, replace "summary" (#1622)
This commit is contained in:
@@ -163,12 +163,12 @@ a key or key combination for the inserted content.
|
||||
":kbd:`Ctrl+K`, :kbd:`E`", "Insert an ``@entity`` keyword"
|
||||
":kbd:`Ctrl+K`, :kbd:`F`", "Insert a ``@focus`` keyword"
|
||||
":kbd:`Ctrl+K`, :kbd:`G`", "Insert a ``@tag`` keyword"
|
||||
":kbd:`Ctrl+K`, :kbd:`H`", "Insert a short description comment"
|
||||
":kbd:`Ctrl+K`, :kbd:`L`", "Insert a ``@location`` keyword"
|
||||
":kbd:`Ctrl+K`, :kbd:`O`", "Insert an ``@object`` keyword"
|
||||
":kbd:`Ctrl+K`, :kbd:`P`", "Insert a ``@plot`` keyword"
|
||||
":kbd:`Ctrl+K`, :kbd:`S`", "Insert a synopsis comment"
|
||||
":kbd:`Ctrl+K`, :kbd:`T`", "Insert a ``@time`` keyword"
|
||||
":kbd:`Ctrl+K`, :kbd:`U`", "Insert a summary comment"
|
||||
":kbd:`Ctrl+K`, :kbd:`V`", "Insert a ``@pov`` keyword"
|
||||
":kbd:`Ctrl+K`, :kbd:`X`", "Insert a ``@custom`` keyword"
|
||||
":kbd:`Ctrl+K`, :kbd:`Ctrl+Space`", "Insert a thin non-breaking space"
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"Synopsis": "Synopsis",
|
||||
"Summary": "Summary",
|
||||
"Short Description": "Short Description",
|
||||
"Comment": "Comment",
|
||||
"Notes": "Notes",
|
||||
"Tag": "Tag",
|
||||
|
||||
@@ -406,7 +406,7 @@ class ProjectBuilder:
|
||||
|
||||
chSynop = self.tr("Summary of the chapter.")
|
||||
scSynop = self.tr("Summary of the scene.")
|
||||
bfNote = self.tr("A brief description.")
|
||||
bfNote = self.tr("A short description.")
|
||||
|
||||
# Create chapters
|
||||
if numChapters > 0:
|
||||
@@ -450,7 +450,7 @@ class ProjectBuilder:
|
||||
aDoc.writeDocument(
|
||||
f"# {noteTitles[newRoot]}\n\n"
|
||||
f"@tag: {ntTag}\n\n"
|
||||
f"% Summary: {bfNote}\n\n"
|
||||
f"% Short: {bfNote}\n\n"
|
||||
)
|
||||
|
||||
# Also add the archive and trash folders
|
||||
|
||||
@@ -339,7 +339,7 @@ class NWIndex:
|
||||
elif line.startswith("%"):
|
||||
if cTitle != TT_NONE:
|
||||
cStyle, cText, _ = processComment(line)
|
||||
if cStyle in (nwComment.SYNOPSIS, nwComment.SUMMARY):
|
||||
if cStyle in (nwComment.SYNOPSIS, nwComment.SHORT):
|
||||
self._itemIndex.setHeadingSynopsis(tHandle, cTitle, cText)
|
||||
|
||||
# Count words for remaining text after last heading
|
||||
@@ -1268,7 +1268,7 @@ class IndexHeading:
|
||||
# =============================================================================================== #
|
||||
|
||||
CLASSIFIERS = {
|
||||
"summary": nwComment.SUMMARY,
|
||||
"short": nwComment.SHORT,
|
||||
"synopsis": nwComment.SYNOPSIS,
|
||||
}
|
||||
|
||||
|
||||
@@ -289,7 +289,7 @@ class ToHtml(Tokenizer):
|
||||
elif tType == self.T_SYNOPSIS and self._doSynopsis:
|
||||
lines.append(self._formatSynopsis(tText, True))
|
||||
|
||||
elif tType == self.T_SUMMARY and self._doSynopsis:
|
||||
elif tType == self.T_SHORT and self._doSynopsis:
|
||||
lines.append(self._formatSynopsis(tText, False))
|
||||
|
||||
elif tType == self.T_COMMENT and self._doComments:
|
||||
@@ -459,7 +459,10 @@ class ToHtml(Tokenizer):
|
||||
|
||||
def _formatSynopsis(self, text: str, synopsis: bool) -> str:
|
||||
"""Apply HTML formatting to synopsis."""
|
||||
sSynop = self._localLookup("Synopsis") if synopsis else self._localLookup("Summary")
|
||||
if synopsis:
|
||||
sSynop = self._localLookup("Synopsis")
|
||||
else:
|
||||
sSynop = self._localLookup("Short Description")
|
||||
if self._genMode == self.M_PREVIEW:
|
||||
return f"<p class='comment'><span class='synopsis'>{sSynop}:</span> {text}</p>\n"
|
||||
else:
|
||||
|
||||
@@ -80,7 +80,7 @@ class Tokenizer(ABC):
|
||||
# Block Type
|
||||
T_EMPTY = 1 # Empty line (new paragraph)
|
||||
T_SYNOPSIS = 2 # Synopsis comment
|
||||
T_SUMMARY = 3 # Summary comment
|
||||
T_SHORT = 3 # Short description comment
|
||||
T_COMMENT = 4 # Comment line
|
||||
T_KEYWORD = 5 # Command line
|
||||
T_TITLE = 6 # Title
|
||||
@@ -470,9 +470,9 @@ class Tokenizer(ABC):
|
||||
))
|
||||
if self._doSynopsis and self._keepMarkdown:
|
||||
tmpMarkdown.append("%s\n" % aLine)
|
||||
elif cStyle == nwComment.SUMMARY:
|
||||
elif cStyle == nwComment.SHORT:
|
||||
self._tokens.append((
|
||||
self.T_SUMMARY, nHead, cText, None, sAlign
|
||||
self.T_SHORT, nHead, cText, None, sAlign
|
||||
))
|
||||
if self._doSynopsis and self._keepMarkdown:
|
||||
tmpMarkdown.append("%s\n" % aLine)
|
||||
|
||||
@@ -170,8 +170,8 @@ class ToMarkdown(Tokenizer):
|
||||
label = self._localLookup("Synopsis")
|
||||
lines.append(f"**{label}:** {tText}\n\n")
|
||||
|
||||
elif tType == self.T_SUMMARY and self._doSynopsis:
|
||||
label = self._localLookup("Summary")
|
||||
elif tType == self.T_SHORT and self._doSynopsis:
|
||||
label = self._localLookup("Short Description")
|
||||
lines.append(f"**{label}:** {tText}\n\n")
|
||||
|
||||
elif tType == self.T_COMMENT and self._doComments:
|
||||
|
||||
@@ -484,7 +484,7 @@ class ToOdt(Tokenizer):
|
||||
tTemp, fTemp = self._formatSynopsis(tText, True)
|
||||
self._addTextPar("Text_20_Meta", oStyle, tTemp, tFmt=fTemp)
|
||||
|
||||
elif tType == self.T_SUMMARY and self._doSynopsis:
|
||||
elif tType == self.T_SHORT and self._doSynopsis:
|
||||
tTemp, fTemp = self._formatSynopsis(tText, False)
|
||||
self._addTextPar("Text_20_Meta", oStyle, tTemp, tFmt=fTemp)
|
||||
|
||||
@@ -558,7 +558,10 @@ class ToOdt(Tokenizer):
|
||||
|
||||
def _formatSynopsis(self, text: str, synopsis: bool) -> tuple[str, list[tuple[int, int]]]:
|
||||
"""Apply formatting to synopsis lines."""
|
||||
name = self._localLookup("Synopsis") if synopsis else self._localLookup("Summary")
|
||||
if synopsis:
|
||||
name = self._localLookup("Synopsis")
|
||||
else:
|
||||
name = self._localLookup("Short Description")
|
||||
rTxt = f"{name}: {text}"
|
||||
rFmt = [(0, self.FMT_B_B), (len(name) + 1, self.FMT_B_E)]
|
||||
return rTxt, rFmt
|
||||
|
||||
+2
-2
@@ -65,7 +65,7 @@ class nwComment(Enum):
|
||||
|
||||
PLAIN = 0
|
||||
SYNOPSIS = 1
|
||||
SUMMARY = 2
|
||||
SHORT = 2
|
||||
|
||||
# END Enum nwComment
|
||||
|
||||
@@ -136,7 +136,7 @@ class nwDocInsert(Enum):
|
||||
QUOTE_LD = 3
|
||||
QUOTE_RD = 4
|
||||
SYNOPSIS = 5
|
||||
SUMMARY = 6
|
||||
SHORT = 6
|
||||
NEW_PAGE = 7
|
||||
VSPACE_S = 8
|
||||
VSPACE_M = 9
|
||||
|
||||
@@ -834,8 +834,8 @@ class GuiDocEditor(QPlainTextEdit):
|
||||
text = "% Synopsis: "
|
||||
newBlock = True
|
||||
goAfter = True
|
||||
elif insert == nwDocInsert.SUMMARY:
|
||||
text = "% Summary: "
|
||||
elif insert == nwDocInsert.SHORT:
|
||||
text = "% Short: "
|
||||
newBlock = True
|
||||
goAfter = True
|
||||
elif insert == nwDocInsert.NEW_PAGE:
|
||||
|
||||
@@ -316,13 +316,13 @@ class _ViewPanelBackRefs(QTreeWidget):
|
||||
|
||||
class _ViewPanelKeyWords(QTreeWidget):
|
||||
|
||||
C_DATA = 0
|
||||
C_NAME = 0
|
||||
C_EDIT = 1
|
||||
C_VIEW = 2
|
||||
C_DOC = 3
|
||||
C_TITLE = 4
|
||||
C_SUMMARY = 5
|
||||
C_DATA = 0
|
||||
C_NAME = 0
|
||||
C_EDIT = 1
|
||||
C_VIEW = 2
|
||||
C_DOC = 3
|
||||
C_TITLE = 4
|
||||
C_SHORT = 5
|
||||
|
||||
D_TAG = Qt.ItemDataRole.UserRole
|
||||
|
||||
@@ -337,7 +337,7 @@ class _ViewPanelKeyWords(QTreeWidget):
|
||||
|
||||
self.setHeaderLabels([
|
||||
self.tr("Tag"), "", "", self.tr("Document"),
|
||||
self.tr("Heading"), self.tr("Summary")
|
||||
self.tr("Heading"), self.tr("Short Description")
|
||||
])
|
||||
self.setIndentation(0)
|
||||
self.setIconSize(QSize(iPx, iPx))
|
||||
@@ -401,7 +401,7 @@ class _ViewPanelKeyWords(QTreeWidget):
|
||||
trItem.setText(self.C_DOC, nwItem.itemName)
|
||||
trItem.setText(self.C_TITLE, hItem.title)
|
||||
trItem.setData(self.C_TITLE, Qt.ItemDataRole.DecorationRole, hDec)
|
||||
trItem.setText(self.C_SUMMARY, hItem.synopsis)
|
||||
trItem.setText(self.C_SHORT, hItem.synopsis)
|
||||
trItem.setData(self.C_DATA, self.D_TAG, tag)
|
||||
|
||||
if tag not in self._treeMap:
|
||||
|
||||
@@ -564,11 +564,11 @@ class GuiMainMenu(QMenuBar):
|
||||
lambda: self.requestDocInsert.emit(nwDocInsert.SYNOPSIS)
|
||||
)
|
||||
|
||||
# Insert > Summary Comment
|
||||
self.aInsSummary = self.mInsComments.addAction(self.tr("Summary Comment"))
|
||||
self.aInsSummary.setShortcut("Ctrl+K, U")
|
||||
self.aInsSummary.triggered.connect(
|
||||
lambda: self.requestDocInsert.emit(nwDocInsert.SUMMARY)
|
||||
# Insert > Short Description Comment
|
||||
self.aInsShort = self.mInsComments.addAction(self.tr("Short Description Comment"))
|
||||
self.aInsShort.setShortcut("Ctrl+K, U")
|
||||
self.aInsShort.triggered.connect(
|
||||
lambda: self.requestDocInsert.emit(nwDocInsert.SHORT)
|
||||
)
|
||||
|
||||
# Insert > Symbols
|
||||
|
||||
@@ -1461,7 +1461,7 @@ class GuiMain(QMainWindow):
|
||||
self.addAction(self.mainMenu.aInsTimes)
|
||||
self.addAction(self.mainMenu.aInsDivide)
|
||||
self.addAction(self.mainMenu.aInsSynopsis)
|
||||
self.addAction(self.mainMenu.aInsSummary)
|
||||
self.addAction(self.mainMenu.aInsShort)
|
||||
|
||||
for mAction, _ in self.mainMenu.mInsKWItems.values():
|
||||
self.addAction(mAction)
|
||||
|
||||
@@ -7,6 +7,6 @@
|
||||
|
||||
@tag: John
|
||||
|
||||
% Summary: The sidekick
|
||||
% Short: The sidekick
|
||||
|
||||
He’s pretty cool. Not Brad Pitt though.
|
||||
|
||||
@@ -7,6 +7,6 @@
|
||||
|
||||
@tag: Jane
|
||||
|
||||
% Summary: The heroine
|
||||
% Short: The heroine
|
||||
|
||||
She’s pretty cool. Not Angelina Jolie though.
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
<?xml version='1.0' encoding='utf-8'?>
|
||||
<novelWriterXML appVersion="2.2-beta1" hexVersion="0x020200b1" fileVersion="1.5" fileRevision="1" timeStamp="2023-11-25 18:16:17">
|
||||
<project id="e2be99af-f9bf-4403-857a-c3d1ac25abea" saveCount="1612" autoCount="256" editTime="81268">
|
||||
<novelWriterXML appVersion="2.2-beta1" hexVersion="0x020200b1" fileVersion="1.5" fileRevision="1" timeStamp="2023-11-26 13:57:28">
|
||||
<project id="e2be99af-f9bf-4403-857a-c3d1ac25abea" saveCount="1613" autoCount="256" editTime="81286">
|
||||
<name>Sample Project</name>
|
||||
<title>Sample Project</title>
|
||||
<author>Jane Smith</author>
|
||||
|
||||
@@ -1280,14 +1280,14 @@ def testCoreIndex_processComment():
|
||||
assert processComment("% \t SYNOPSIS : Hi") == (nwComment.SYNOPSIS, "Hi", 16)
|
||||
assert processComment("% \t SYNOPSIS : Hi:You") == (nwComment.SYNOPSIS, "Hi:You", 16)
|
||||
|
||||
# Summary
|
||||
assert processComment("%summary:") == (nwComment.PLAIN, "summary:", 0)
|
||||
assert processComment("%summary: Hi") == (nwComment.SUMMARY, "Hi", 9)
|
||||
assert processComment("% summary: Hi") == (nwComment.SUMMARY, "Hi", 10)
|
||||
assert processComment("% summary : Hi") == (nwComment.SUMMARY, "Hi", 12)
|
||||
assert processComment("% Summary : Hi") == (nwComment.SUMMARY, "Hi", 14)
|
||||
assert processComment("% \t SUMMARY : Hi") == (nwComment.SUMMARY, "Hi", 15)
|
||||
assert processComment("% \t SUMMARY : Hi:You") == (nwComment.SUMMARY, "Hi:You", 15)
|
||||
# Short Description
|
||||
assert processComment("%short:") == (nwComment.PLAIN, "short:", 0)
|
||||
assert processComment("%short: Hi") == (nwComment.SHORT, "Hi", 7)
|
||||
assert processComment("% short: Hi") == (nwComment.SHORT, "Hi", 8)
|
||||
assert processComment("% short : Hi") == (nwComment.SHORT, "Hi", 10)
|
||||
assert processComment("% Short : Hi") == (nwComment.SHORT, "Hi", 12)
|
||||
assert processComment("% \t SHORT : Hi") == (nwComment.SHORT, "Hi", 13)
|
||||
assert processComment("% \t SHORT : Hi:You") == (nwComment.SHORT, "Hi:You", 13)
|
||||
|
||||
# END Test testCoreIndex_processComment
|
||||
|
||||
|
||||
@@ -149,7 +149,7 @@ def testCoreToHtml_ConvertFormat(mockGUI):
|
||||
"<p class='break'>Line one<br/>Line two<br/>Line three</p>\n"
|
||||
)
|
||||
|
||||
# Synopsis, Summary
|
||||
# Synopsis, Short
|
||||
html._text = "%synopsis: The synopsis ...\n"
|
||||
html.tokenizeText()
|
||||
html.doConvert()
|
||||
@@ -164,11 +164,11 @@ def testCoreToHtml_ConvertFormat(mockGUI):
|
||||
)
|
||||
|
||||
html.setSynopsis(True)
|
||||
html._text = "%summary: A description ...\n"
|
||||
html._text = "%short: A short description ...\n"
|
||||
html.tokenizeText()
|
||||
html.doConvert()
|
||||
assert html.theResult == (
|
||||
"<p class='synopsis'><strong>Summary:</strong> A description ...</p>\n"
|
||||
"<p class='synopsis'><strong>Short Description:</strong> A short description ...</p>\n"
|
||||
)
|
||||
|
||||
# Comment
|
||||
@@ -621,8 +621,8 @@ def testCoreToHtml_Format(mockGUI):
|
||||
assert html._formatSynopsis("synopsis text", True) == (
|
||||
"<p class='synopsis'><strong>Synopsis:</strong> synopsis text</p>\n"
|
||||
)
|
||||
assert html._formatSynopsis("summary text", False) == (
|
||||
"<p class='synopsis'><strong>Summary:</strong> summary text</p>\n"
|
||||
assert html._formatSynopsis("short text", False) == (
|
||||
"<p class='synopsis'><strong>Short Description:</strong> short text</p>\n"
|
||||
)
|
||||
assert html._formatComments("comment text") == (
|
||||
"<p class='comment'><strong>Comment:</strong> comment text</p>\n"
|
||||
@@ -646,8 +646,8 @@ def testCoreToHtml_Format(mockGUI):
|
||||
assert html._formatSynopsis("synopsis text", True) == (
|
||||
"<p class='comment'><span class='synopsis'>Synopsis:</span> synopsis text</p>\n"
|
||||
)
|
||||
assert html._formatSynopsis("summary text", False) == (
|
||||
"<p class='comment'><span class='synopsis'>Summary:</span> summary text</p>\n"
|
||||
assert html._formatSynopsis("short text", False) == (
|
||||
"<p class='comment'><span class='synopsis'>Short Description:</span> short text</p>\n"
|
||||
)
|
||||
assert html._formatComments("comment text") == (
|
||||
"<p class='comment'>comment text</p>\n"
|
||||
|
||||
@@ -471,19 +471,19 @@ def testCoreToken_MetaFormat(mockGUI):
|
||||
tokens.tokenizeText()
|
||||
assert tokens.theMarkdown[-1] == "% synopsis: The synopsis\n\n"
|
||||
|
||||
# Summary
|
||||
# Short
|
||||
tokens.setSynopsis(False)
|
||||
tokens._text = "% summary: A description\n"
|
||||
tokens._text = "% short: A short description\n"
|
||||
tokens.tokenizeText()
|
||||
assert tokens._tokens == [
|
||||
(Tokenizer.T_SUMMARY, 0, "A description", None, Tokenizer.A_NONE),
|
||||
(Tokenizer.T_SHORT, 0, "A short description", None, Tokenizer.A_NONE),
|
||||
(Tokenizer.T_EMPTY, 0, "", None, Tokenizer.A_NONE),
|
||||
]
|
||||
assert tokens.theMarkdown[-1] == "\n"
|
||||
|
||||
tokens.setSynopsis(True)
|
||||
tokens.tokenizeText()
|
||||
assert tokens.theMarkdown[-1] == "% summary: A description\n\n"
|
||||
assert tokens.theMarkdown[-1] == "% short: A short description\n\n"
|
||||
|
||||
# Keyword
|
||||
tokens._text = "@char: Bod\n"
|
||||
|
||||
@@ -106,7 +106,7 @@ def testCoreToMarkdown_ConvertFormat(mockGUI):
|
||||
theMD.doConvert()
|
||||
assert theMD.theResult == "Line one \nLine two \nLine three\n\n"
|
||||
|
||||
# Synopsis, Summary
|
||||
# Synopsis, Short
|
||||
theMD._text = "%synopsis: The synopsis ...\n"
|
||||
theMD.tokenizeText()
|
||||
theMD.doConvert()
|
||||
@@ -119,10 +119,10 @@ def testCoreToMarkdown_ConvertFormat(mockGUI):
|
||||
assert theMD.theResult == "**Synopsis:** The synopsis ...\n\n"
|
||||
|
||||
theMD.setSynopsis(True)
|
||||
theMD._text = "%summary: A description ...\n"
|
||||
theMD._text = "%short: A description ...\n"
|
||||
theMD.tokenizeText()
|
||||
theMD.doConvert()
|
||||
assert theMD.theResult == "**Summary:** A description ...\n\n"
|
||||
assert theMD.theResult == "**Short Description:** A description ...\n\n"
|
||||
|
||||
# Comment
|
||||
theMD._text = "% A comment ...\n"
|
||||
|
||||
@@ -447,12 +447,12 @@ def testCoreToOdt_Convert(mockGUI):
|
||||
'</office:text>'
|
||||
)
|
||||
|
||||
# Synopsis, Summary, Comment, Keywords
|
||||
# Synopsis, Short, Comment, Keywords
|
||||
odt._text = (
|
||||
"### Scene\n\n"
|
||||
"@pov: Jane\n\n"
|
||||
"% synopsis: So it begins\n\n"
|
||||
"% summary: Then what\n\n"
|
||||
"% short: Then what\n\n"
|
||||
"% A plain comment\n\n"
|
||||
)
|
||||
odt.setSynopsis(True)
|
||||
@@ -471,7 +471,7 @@ def testCoreToOdt_Convert(mockGUI):
|
||||
'<text:p text:style-name="Text_20_Meta"><text:span text:style-name="T7">'
|
||||
'Synopsis:</text:span> So it begins</text:p>'
|
||||
'<text:p text:style-name="Text_20_Meta"><text:span text:style-name="T7">'
|
||||
'Summary:</text:span> Then what</text:p>'
|
||||
'Short Description:</text:span> Then what</text:p>'
|
||||
'<text:p text:style-name="Text_20_Meta"><text:span text:style-name="T7">'
|
||||
'Comment:</text:span> A plain comment</text:p>'
|
||||
'</office:text>'
|
||||
@@ -810,8 +810,8 @@ def testCoreToOdt_Format(mockGUI):
|
||||
assert odt._formatSynopsis("synopsis text", True) == (
|
||||
"Synopsis: synopsis text", [(0, ToOdt.FMT_B_B), (9, ToOdt.FMT_B_E)]
|
||||
)
|
||||
assert odt._formatSynopsis("summary text", False) == (
|
||||
"Summary: summary text", [(0, ToOdt.FMT_B_B), (8, ToOdt.FMT_B_E)]
|
||||
assert odt._formatSynopsis("short text", False) == (
|
||||
"Short Description: short text", [(0, ToOdt.FMT_B_B), (18, ToOdt.FMT_B_E)]
|
||||
)
|
||||
assert odt._formatComments("comment text") == (
|
||||
"Comment: comment text", [(0, ToOdt.FMT_B_B), (8, ToOdt.FMT_B_E)]
|
||||
|
||||
@@ -594,8 +594,8 @@ def testGuiMenu_Insert(qtbot, monkeypatch, nwGUI, fncPath, projPath, mockRnd):
|
||||
assert nwGUI.docEditor.getText() == "Stuff\n% Synopsis: \n"
|
||||
|
||||
nwGUI.docEditor.setPlainText("Stuff\n")
|
||||
nwGUI.mainMenu.aInsSummary.activate(QAction.Trigger)
|
||||
assert nwGUI.docEditor.getText() == "Stuff\n% Summary: \n"
|
||||
nwGUI.mainMenu.aInsShort.activate(QAction.Trigger)
|
||||
assert nwGUI.docEditor.getText() == "Stuff\n% Short: \n"
|
||||
|
||||
# Insert Break or Space
|
||||
# =====================
|
||||
|
||||
Reference in New Issue
Block a user