Skip to content

Commit 05e28e2

Browse files
committed
Fix escape sequences + update INI documentation
1 parent fc77592 commit 05e28e2

6 files changed

Lines changed: 57 additions & 32 deletions

File tree

Legacy-v2.1/Src/WebEditUVer.ob2

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
MODULE WebEditUVer;
22

33
CONST
4-
String* = '2.8.1.1';
4+
String* = '2.8.1.2';
55

66
END WebEditUVer.

Legacy-v2.1/Src/WebEditUVer.rc

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
MAINICON ICON "..\..\Logo.ico"
2-
#define WEBEDIT_VERSION_STRING "2.8.1.1\000"
3-
#define WEBEDIT_VERSION_WORDS 2,8,1,1
2+
#define WEBEDIT_VERSION_STRING "2.8.1.2\000"
3+
#define WEBEDIT_VERSION_WORDS 2,8,1,2
44

55
1 VERSIONINFO
66
FILEVERSION WEBEDIT_VERSION_WORDS
@@ -18,7 +18,7 @@ BLOCK "StringFileInfo"
1818
VALUE "LegalCopyright", "� 2008 - 2010 by Alexander Iljin\000"
1919
VALUE "FileDescription", "WebEdit plugin for Notepad++ (Unicode).\000"
2020
VALUE "FileVersion", WEBEDIT_VERSION_STRING
21-
VALUE "ProductVersion", "2.8.1.1\000"
21+
VALUE "ProductVersion", "2.8.1.2\000"
2222
VALUE "ProductName", "WebEdit\000"
2323
VALUE "InternalName", "WebEdit\000"
2424
VALUE "OriginalFilename", "WebEditU.dll\000"

ReadMe.txt

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,7 @@ v2.8 — New features (examples)
99
- Replaced with the current Windows user name (the user account running Notepad++).
1010
- Example tag line in `WebEdit.ini`:
1111
user=Author: \u|
12-
- \d:"format"
12+
- \d:"format" (experimental)
1313
- Replaced with the local date/time. An optional .NET-style date/time format string may be supplied in quotes.
1414
- Examples:
1515
- `datetime=Created: \d:"yyyy-MM-dd HH:mm:ss"` → inserts date/time in 24h ISO-like format.

WebEdit/Properties/AssemblyInfo.cs

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -27,6 +27,6 @@
2727
// You can specify all the values or you can default the Build and Revision Numbers
2828
// by using the '*' as shown below:
2929
// [assembly: AssemblyVersion("1.0.*")]
30-
[assembly: AssemblyVersion("2.8.1.1")]
31-
[assembly: AssemblyFileVersion("2.8.1.1")]
32-
[assembly: AssemblyInformationalVersion("2.8.1.1")]
30+
[assembly: AssemblyVersion("2.8.1.2")]
31+
[assembly: AssemblyFileVersion("2.8.1.2")]
32+
[assembly: AssemblyInformationalVersion("2.8.1.2")]

WebEdit/Resources/WebEdit.ini

Lines changed: 13 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -57,16 +57,23 @@ T&r=<tr>|</tr>
5757
; characters. The number of Tags is not limited. The pipe character "|" marks
5858
; the caret position after the tag replacement.
5959
; Known escape sequences:
60-
; \c = system clipboard contents
61-
; \i = indentation
60+
; \r = carriage return (for Windows line endings)
6261
; \n = new line
6362
; \t = tab character
64-
; \d:"..." = Local date/time in the format specified between the quotes, e.g. \d:"Y-m-d H:i:s" (2025-12-31 23:59:59)
63+
; \i = indentation
64+
; \c = system clipboard contents
6565
; \u = Windows username
66+
; \x = current filename (without path) / document name
67+
; \p = current full file path (including filename) / document name
68+
; \d:"..." = Local date/time in the format specified between the quotes, e.g. \d:"yyyy-MM-dd HH:mm:ss" (2025-12-31 23:59:59)
6669
; \| = |
67-
; \\ = \
70+
; \\ = \ (for the sequences above, e.g. \\c, \\i etc. -- except.: \|, as it is already escaped)
6871

6972
; MIXED
73+
docs=/**\n * @file \x\n * @brief Description|\n * @author \u <mail@example.com>\n * @date \d:"yyyy-MM-dd"\n */
74+
dox={**\n * @file \x\n * @brief Description|\n * @author \u <mail@example.com>\n * @date \d:"yyyy-MM-dd"\n *\n * @param string $param Parameter_Description\n * @param etc.\n *\n * @details For more imformation see: \n *}
75+
func=/**\n * Description|\n *\n * @param string $var1 param1\n * @param bool $var2 param2\n * @return True on success, false otherwise\n *\n * @details Throw an exception in case of error!\n */
76+
param=* @param string $var| Parameter_Description
7077
yx="|" => "",
7178
ar=array();
7279
arr=array(|)
@@ -89,7 +96,6 @@ ne=!= "|"
8996
neq=!= "|"
9097
iq=== "|"
9198
eq=== "|"
92-
; gt --> gte, lt --> lte
9399
gt=>=
94100
ltt=<=
95101
iff=if (|) \n\i\n
@@ -116,6 +122,8 @@ nn= . "\\n";
116122
k=/* | */
117123
g=global $|;
118124
gl=global $|;
125+
lorem=Lorem ipsum dolor sit amet
126+
lipsum=Lorem ipsum dolor sit amet, consectetur adipiscing elit. Nulla fringilla pharetra fermentum.\nVestibulum neque erat, bibendum ac sagittis et, pulvinar at urna. Donec sit amet ipsum quis velit cursus ultrices elementum id lacus.\nSed vel massa vitae turpis viverra adipiscing at nec odio. Quisque ac ligula metus. Vestibulum suscipit elit eget lacus pellentesque tempus. Suspendisse potenti.
119127

120128
; ECHOING
121129
1='|'
@@ -704,8 +712,6 @@ SUB=SUBSTRING(date|, 1, -3)
704712
SI=SUBSTRING_INDEX(datetime|, ' ', 1)
705713
POS=SUBSTRING_INDEX(datetime|, ' ', 1)
706714
STR=LOCATE('|', )
707-
INV=SELECT * FROM t11_order_headers oh LEFT JOIN t11_order_items oi ON oi.header_id = oh.id WHERE | IN (
708-
SOH=SELECT * FROM t11_order_headers oh LEFT JOIN t11_order_items oi ON oi.header_id = oh.id WHERE |
709715
LEN=LENGTH(|) =
710716
REP=REPLACE(colname|, 'from', 'to')
711717
CAST=CAST(| AS UNSIGNED);

WebEdit/Tags.cs

Lines changed: 36 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -17,7 +17,7 @@ partial class Tags(long tabStartPos, long tabEndPos)
1717
/// \n with a new line string determined by current EOL mode
1818
/// \t with the tab character
1919
/// \| with |
20-
/// \\ with \
20+
/// \\ with \ (UNNECESSARY/DEPRECATED)
2121
/// </code>
2222
/// </summary>
2323
/// <param name="value">Input string from the ini-file's value of the tag.</param>
@@ -27,19 +27,24 @@ partial class Tags(long tabStartPos, long tabEndPos)
2727
/// </remarks>
2828
internal string Unescape(string value)
2929
{
30-
StringBuilder text = new(value);
3130
ScintillaGateway sci = new(Utils.GetCurrentScintilla());
3231
sci.SetTargetRange(_tabStartPos, _tabEndPos);
3332
string indent = sci.GetTargetText();
34-
// literal DOS EOL
35-
text.Replace("\\r\\n", $"\r\n{indent}");
36-
// literal carriage return
37-
text.Replace("\\r", $"\r{indent}");
38-
// document-specific EOL
39-
text.Replace("\\n", $"{sci.LineDelimiter}{indent}");
40-
text.Replace("\\t", "\t");
41-
text.Replace("\\|", "|");
42-
text.Replace("\\\\", "\\");
33+
value = Regex.Replace(value, "(?<!\\\\)\\\\r(?<!\\\\)\\\\n", $"\r\n{indent}"); // literal DOS EOL
34+
value = Regex.Replace(value, "(?<!\\\\)\\\\r", $"\r{indent}"); // literal carriage return
35+
value = Regex.Replace(value, "(?<!\\\\)\\\\n", $"\n{indent}"); // document-specific EOL
36+
value = Regex.Replace(value, "(?<!\\\\)\\\\t", $"\t{indent}"); // tab character
37+
value = Regex.Replace(value, "(?<!\\\\)\\|", $"|{indent}"); // cursor
38+
// value = Regex.Replace(value, "\\\\", "\\"); // escape character (not needed)
39+
40+
// Handle escaped sequences
41+
StringBuilder text = new(value);
42+
text.Replace("\\\\r\\\\n", "\\r\\n"); // literal DOS EOL (escaped)
43+
text.Replace("\\\\r", "\\r"); // literal carriage return (escaped)
44+
text.Replace("\\\\n", "\\n"); // document-specific EOL (escaped)
45+
text.Replace("\\\\t", "\\t"); // tab character (escaped)
46+
text.Replace("\\|", "|"); // cursor (escaped)
47+
// text.Replace("\\\\", "\\"); // escape character (not needed)
4348
return text.ToString();
4449
}
4550

@@ -70,12 +75,11 @@ internal bool FindAndReplace(long startPos)
7075
{
7176
{"\\f", PasteFileContents},
7277
{"\\c", sci.Paste},
73-
{"\\d", PasteDateTime},
7478
{"\\u", PasteUserName},
7579
{"\\x", PasteFileName},
7680
{"\\p", PasteFilePath},
77-
// must come last as the caret will be restored here
78-
{"\\i", sci.Tab}
81+
{"\\d", PasteDateTime},
82+
{"\\i", sci.Tab} // must come last as the caret will be restored here!
7983
};
8084

8185
foreach ((string seq, var replaceFunc) in replacements)
@@ -93,9 +97,23 @@ internal bool FindAndReplace(long startPos)
9397
seqStart += sci.CodePage.GetByteCount(tmpTargetText) - tmpTargetText.Length; // Adjust for multi-byte characters
9498
long selStart = sci.GetTargetStart() + seqStart;
9599
sci.SetSelection(selStart, selStart + seq.Length); // sci.CodePage.GetByteCount(seq)
96-
replaceFunc();
100+
if (seqStart == 0 || sci.GetCharAt(selStart - 1) != 92) // Backspace (\)
101+
{
102+
replaceFunc();
103+
}
104+
else
105+
{
106+
sci.SetSelection(selStart - 1, selStart + seq.Length);
107+
sci.ReplaceSel(seq);
108+
rangeEnd--;
109+
}
110+
sci.SetCurrentPos(sci.GetSelectionEnd());
97111
rangeEnd += (sci.GetSelectionEnd() - selStart) - seq.Length; // sci.CodePage.GetByteCount(seq)
98112

113+
// Capture the first date only!
114+
if (seq == "\\d")
115+
break; // TODO: replacing the first occurrence (Unicode issue?) -- rangeEnd may be wrong as using `seq.Length`!
116+
99117
// capture the caret position produced by the first '\i' replacement
100118
if (seq == "\\i" && firstIndentCaret == -1)
101119
firstIndentCaret = sci.GetSelectionEnd();
@@ -200,7 +218,8 @@ private void PasteDateTime()
200218
int matchEnd = matchStart + match.Length;
201219
sci.SetSelection(sci.GetTargetStart() + matchStart, sci.GetTargetStart() + matchEnd);
202220
sci.ReplaceSel(formattedDate);
203-
offset += formattedDate.Length - match.Length;
221+
return; // Hotfix: only replace the first occurrence (Unicode issue?)
222+
// offset += (formattedDate.Length - match.Length);
204223
}
205224

206225
}
@@ -249,7 +268,7 @@ private void PasteFilePath()
249268
/// <remarks>
250269
/// For custom date/time format strings see: <see href="https://learn.microsoft.com/en-us/dotnet/standard/base-types/custom-date-and-time-format-strings"/>
251270
/// </remarks>
252-
[GeneratedRegex(@"\\d:[""']([^""']+)[""']")]
271+
[GeneratedRegex(@"(?<!\\)\\d:[""']([^""']+)[""']")]
253272
private static partial Regex UserDefinedDateRegex();
254273

255274
private readonly long _tabStartPos = tabStartPos;

0 commit comments

Comments
 (0)