@magic-xpa/utils 4.1200.0-dev4120.4 → 4.1200.0-dev4120.41
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/fesm2022/magic-xpa-utils.mjs +1215 -72
- package/fesm2022/magic-xpa-utils.mjs.map +1 -1
- package/index.d.ts +3 -0
- package/package.json +2 -4
- package/src/MsgInterface.d.ts +2 -0
- package/src/StrUtil.d.ts +1 -0
- package/esm2022/index.mjs +0 -27
- package/esm2022/magic-xpa-utils.mjs +0 -2
- package/esm2022/src/Base64.mjs +0 -164
- package/esm2022/src/ChoiceUtils.mjs +0 -79
- package/esm2022/src/Constants.mjs +0 -74
- package/esm2022/src/DateTimeUtils.mjs +0 -54
- package/esm2022/src/DateUtil.mjs +0 -58
- package/esm2022/src/InternalInterface.mjs +0 -341
- package/esm2022/src/JSON_Utils.mjs +0 -7
- package/esm2022/src/Logger.mjs +0 -216
- package/esm2022/src/MagicConstants.mjs +0 -12
- package/esm2022/src/Misc.mjs +0 -98
- package/esm2022/src/MsgInterface.mjs +0 -192
- package/esm2022/src/PICInterface.mjs +0 -60
- package/esm2022/src/PlatformUtils.mjs +0 -11
- package/esm2022/src/Queue.mjs +0 -28
- package/esm2022/src/Randomizer.mjs +0 -34
- package/esm2022/src/RequestInfo.mjs +0 -28
- package/esm2022/src/Rtf.mjs +0 -614
- package/esm2022/src/StorageAttribute.mjs +0 -84
- package/esm2022/src/StrUtil.mjs +0 -453
- package/esm2022/src/SyncExecutionHelper.mjs +0 -21
- package/esm2022/src/UtilDateJpn.mjs +0 -232
- package/esm2022/src/UtilImeJpn.mjs +0 -13
- package/esm2022/src/UtilStrByteMode.mjs +0 -300
- package/esm2022/src/XMLConstants.mjs +0 -169
- package/esm2022/src/Xml/XmlParser.mjs +0 -247
- package/esm2022/src/enums.mjs +0 -1763
|
@@ -1,33 +1,90 @@
|
|
|
1
1
|
import { Encoding, StringBuilder, Hashtable, Stack, NChar, NNumber, NString, RefParam, isNullOrUndefined, DateTime, ISO_8859_1_Encoding, ApplicationException, Int32, Exception, List, Thread, Debug } from '@magic-xpa/mscorelib';
|
|
2
2
|
import { parseString } from 'xml2js';
|
|
3
3
|
|
|
4
|
+
/// <summary>JPN: DBCS support
|
|
5
|
+
/// Utility Class for String
|
|
6
|
+
/// In this class, considering DBCS, strings are counted by the number
|
|
7
|
+
/// of bytes, not the number of characters.
|
|
8
|
+
/// </summary>
|
|
9
|
+
/// <author> Toshiro Nakayoshi (MSJ) </author>
|
|
4
10
|
class UtilStrByteMode {
|
|
5
11
|
static Encoding = Encoding.UTF8;
|
|
12
|
+
// TODO : need to check what to do with CultureInfo
|
|
6
13
|
static strNavigatorLang = window.navigator.language;
|
|
7
14
|
static _bLocaleDefLangJPN = UtilStrByteMode.strNavigatorLang.startsWith('ja');
|
|
8
15
|
static _bLocaleDefLangCHN = UtilStrByteMode.strNavigatorLang.startsWith('zh');
|
|
9
16
|
static _bLocaleDefLangKOR = UtilStrByteMode.strNavigatorLang.startsWith('ko');
|
|
17
|
+
/// <summary> Checks the environment whether it is running on DBCS environment
|
|
18
|
+
/// Returns true if the language code for the current default Locale is
|
|
19
|
+
/// DBCS language (in non-Unicode encoding).
|
|
20
|
+
///
|
|
21
|
+
/// </summary>
|
|
22
|
+
/// <returns> true if DBCS, or false if SBCS
|
|
23
|
+
/// </returns>
|
|
10
24
|
static isLocaleDefLangDBCS() {
|
|
11
25
|
return UtilStrByteMode._bLocaleDefLangJPN || UtilStrByteMode._bLocaleDefLangCHN || UtilStrByteMode._bLocaleDefLangKOR;
|
|
12
26
|
}
|
|
27
|
+
/// <summary> Checks whether the language code for the current default Locale
|
|
28
|
+
/// is JAPANESE.
|
|
29
|
+
///
|
|
30
|
+
/// </summary>
|
|
31
|
+
/// <returns> true if JAPANESE, or false if not
|
|
32
|
+
/// </returns>
|
|
13
33
|
static isLocaleDefLangJPN() {
|
|
14
34
|
return UtilStrByteMode._bLocaleDefLangJPN;
|
|
15
35
|
}
|
|
36
|
+
/// <summary> Checks whether the language code for the current default Locale
|
|
37
|
+
/// is KOREAN.
|
|
38
|
+
///
|
|
39
|
+
/// </summary>
|
|
40
|
+
/// <returns> true if KOREAN, or false if not
|
|
41
|
+
/// </returns>
|
|
16
42
|
static isLocaleDefLangKOR() {
|
|
17
43
|
return UtilStrByteMode._bLocaleDefLangKOR;
|
|
18
44
|
}
|
|
19
45
|
static isKoreanCharacter(c) {
|
|
20
|
-
return (44032 <= c && c <= 55203) || (4352 <= c && c <= 4607) || (12592 <= c && c <= 12687) || (43360 <= c && c <= 43391) || (55216 <= c && c <= 55295);
|
|
21
|
-
}
|
|
46
|
+
return (44032 <= /*'가'*/ c && c <= 55203 /*'힣'*/) || (4352 <= /*'ᄀ'*/ c && c <= 4607 /*'ᇿ'*/) || (12592 <= /*''*/ c && c <= 12687 /*''*/) || (43360 <= /*'ꥠ'*/ c && c <= 43391 /*''*/) || (55216 <= /*'ힰ'*/ c && c <= 55295 /*''*/);
|
|
47
|
+
}
|
|
48
|
+
/// <summary> Length of String
|
|
49
|
+
/// Returns the number of bytes (in default encoding).
|
|
50
|
+
///
|
|
51
|
+
/// </summary>
|
|
52
|
+
/// <param name="strVal:">string (in Unicode)
|
|
53
|
+
/// </param>
|
|
54
|
+
/// <returns> the number of bytes (in default encoding)
|
|
55
|
+
///
|
|
56
|
+
/// Example: lenB("abXYc")
|
|
57
|
+
/// Where 'a', 'b' and 'c' are SBCS, and 'X' and 'Y' are DBCS, it returns
|
|
58
|
+
/// 7.
|
|
59
|
+
/// </returns>
|
|
22
60
|
static lenB(strVal) {
|
|
61
|
+
// convert to byte[] by default-encoding
|
|
23
62
|
return UtilStrByteMode.Encoding.GetByteCount(strVal);
|
|
24
63
|
}
|
|
64
|
+
/// <summary> Substring of String
|
|
65
|
+
/// Extracts a specified number of characters (a substring) from a string.
|
|
66
|
+
/// If a DBCS character is divided in two, it will be replace to a space.
|
|
67
|
+
///
|
|
68
|
+
/// </summary>
|
|
69
|
+
/// <param name="strVal:">string (in Unicode)
|
|
70
|
+
/// </param>
|
|
71
|
+
/// <param name="ofs:">starting position (byte) of the substring
|
|
72
|
+
/// </param>
|
|
73
|
+
/// <param name="len:">number of bytes to be extracted (i.e. bytes of substring)
|
|
74
|
+
/// </param>
|
|
75
|
+
/// <returns> substring
|
|
76
|
+
///
|
|
77
|
+
/// Example: midB("abXYc", 2, 4)
|
|
78
|
+
/// Where 'a', 'b' and 'c' are SBCS, and 'X' and 'Y' are DBCS, it returns
|
|
79
|
+
/// "bX ".
|
|
80
|
+
/// </returns>
|
|
25
81
|
static midB(strVal, ofs, len) {
|
|
26
|
-
let intValidMaxIndex = -1;
|
|
27
|
-
let intValidMinIndex = -1;
|
|
28
|
-
let bHeadSpace = false;
|
|
29
|
-
let bEndSpace = false;
|
|
82
|
+
let intValidMaxIndex = -1; // param #1 of substring
|
|
83
|
+
let intValidMinIndex = -1; // param #2 of substring
|
|
84
|
+
let bHeadSpace = false; // flag: need to add space
|
|
85
|
+
let bEndSpace = false; // flag: need to add space
|
|
30
86
|
let strRet;
|
|
87
|
+
// check and modify ofs & len
|
|
31
88
|
if (len <= 0)
|
|
32
89
|
return "";
|
|
33
90
|
if (ofs <= 0) {
|
|
@@ -41,6 +98,7 @@ class UtilStrByteMode {
|
|
|
41
98
|
let LenMax = intByteLength - ofs;
|
|
42
99
|
if (LenMax < len)
|
|
43
100
|
len = LenMax;
|
|
101
|
+
// set MinIndex and MaxIndex for substring
|
|
44
102
|
intByteLength = 0;
|
|
45
103
|
for (let intIndex = 0; intIndex < strVal.length; intIndex = intIndex + 1) {
|
|
46
104
|
let s = strVal.substr(intIndex, 1);
|
|
@@ -68,7 +126,9 @@ class UtilStrByteMode {
|
|
|
68
126
|
}
|
|
69
127
|
}
|
|
70
128
|
}
|
|
129
|
+
// prepare for substring
|
|
71
130
|
let strbufAddingBuf = new StringBuilder(len);
|
|
131
|
+
// execute Mid
|
|
72
132
|
if (bHeadSpace) {
|
|
73
133
|
strbufAddingBuf.Append(' ');
|
|
74
134
|
}
|
|
@@ -82,9 +142,39 @@ class UtilStrByteMode {
|
|
|
82
142
|
strbufAddingBuf = null;
|
|
83
143
|
return strRet;
|
|
84
144
|
}
|
|
145
|
+
/// <summary> Get Characters from Left of String
|
|
146
|
+
/// Returns a specified number of bytes from the left side of a string.
|
|
147
|
+
/// If a DBCS character is divided in two, it will be replace to a space.
|
|
148
|
+
///
|
|
149
|
+
/// </summary>
|
|
150
|
+
/// <param name="strVal:">string (in Unicode)
|
|
151
|
+
/// </param>
|
|
152
|
+
/// <param name="len:">number of bytes to be retured
|
|
153
|
+
/// </param>
|
|
154
|
+
/// <returns> output string
|
|
155
|
+
///
|
|
156
|
+
/// Example: leftB("abXYc", 4)
|
|
157
|
+
/// Where 'a', 'b' and 'c' are SBCS, and 'X' and 'Y' are DBCS, it returns
|
|
158
|
+
/// "abX".
|
|
159
|
+
/// </returns>
|
|
85
160
|
static leftB(strVal, len) {
|
|
86
161
|
return UtilStrByteMode.midB(strVal, 0, len);
|
|
87
162
|
}
|
|
163
|
+
/// <summary> Get Characters from Right of String
|
|
164
|
+
/// Returns a specified number of bytes from the right side of a string.
|
|
165
|
+
/// If a DBCS character is divided in two, it will be replace to a space.
|
|
166
|
+
///
|
|
167
|
+
/// </summary>
|
|
168
|
+
/// <param name="strVal:">string (in Unicode)
|
|
169
|
+
/// </param>
|
|
170
|
+
/// <param name="len:">number of bytes to be retured
|
|
171
|
+
/// </param>
|
|
172
|
+
/// <returns> output string
|
|
173
|
+
///
|
|
174
|
+
/// Example: rightB("abXYc", 4)
|
|
175
|
+
/// Where 'a', 'b' and 'c' are SBCS, and 'X' and 'Y' are DBCS, it returns
|
|
176
|
+
/// " Yc".
|
|
177
|
+
/// </returns>
|
|
88
178
|
static rightB(strVal, len) {
|
|
89
179
|
let byteFldsValLen = UtilStrByteMode.lenB(strVal);
|
|
90
180
|
if (len < 0) {
|
|
@@ -96,6 +186,27 @@ class UtilStrByteMode {
|
|
|
96
186
|
}
|
|
97
187
|
return UtilStrByteMode.midB(strVal, ofs, len);
|
|
98
188
|
}
|
|
189
|
+
/// <summary> Insert String
|
|
190
|
+
/// Inserts one string into another.
|
|
191
|
+
/// If a DBCS character is divided in two, it will be replace to a space.
|
|
192
|
+
///
|
|
193
|
+
/// </summary>
|
|
194
|
+
/// <param name="strTarget:">A string that represents the target string.
|
|
195
|
+
/// </param>
|
|
196
|
+
/// <param name="strSource:">A string that represents the source string.
|
|
197
|
+
/// </param>
|
|
198
|
+
/// <param name="ofs:">A number that represents the starting position (byte) in
|
|
199
|
+
/// the target.
|
|
200
|
+
/// </param>
|
|
201
|
+
/// <param name="len:">A number that represents the number of bytes from the
|
|
202
|
+
/// source that will be inserted into the target.
|
|
203
|
+
/// </param>
|
|
204
|
+
/// <returns> output string
|
|
205
|
+
///
|
|
206
|
+
/// Example: insB("abXYc", "de", 4, 1)
|
|
207
|
+
/// Where 'a', 'b', 'c', 'd' and 'e' are SBCS, and 'X' and 'Y' are DBCS,
|
|
208
|
+
/// it returns "ab d Yc".
|
|
209
|
+
/// </returns>
|
|
99
210
|
static insB(strTarget, strSource, ofs, len) {
|
|
100
211
|
if (ofs < 0) {
|
|
101
212
|
ofs = 0;
|
|
@@ -122,6 +233,24 @@ class UtilStrByteMode {
|
|
|
122
233
|
strbufRetVal.Append(UtilStrByteMode.rightB(strTarget, intTargetLenB - ofs));
|
|
123
234
|
return strbufRetVal.ToString();
|
|
124
235
|
}
|
|
236
|
+
/// <summary> Delete Characters
|
|
237
|
+
/// Delete characters from a string.
|
|
238
|
+
/// If a DBCS character is divided in two, it will be replace to a space.
|
|
239
|
+
///
|
|
240
|
+
/// </summary>
|
|
241
|
+
/// <param name="strVal:">string (in Unicode)
|
|
242
|
+
/// </param>
|
|
243
|
+
/// <param name="ofs:">The position (byte) of the first character to be deleted.
|
|
244
|
+
/// </param>
|
|
245
|
+
/// <param name="len:">The number of characters to be deleted, beginning with
|
|
246
|
+
/// position start and proceeding rightward.
|
|
247
|
+
/// </param>
|
|
248
|
+
/// <returns> output string
|
|
249
|
+
///
|
|
250
|
+
/// Example: delB("abXYc", 2, 4)
|
|
251
|
+
/// Where 'a', 'b' and 'c' are SBCS, and 'X' and 'Y' are DBCS, it returns
|
|
252
|
+
/// "a c".
|
|
253
|
+
/// </returns>
|
|
125
254
|
static delB(strVal, ofs, len) {
|
|
126
255
|
if (ofs < 0) {
|
|
127
256
|
ofs = 0;
|
|
@@ -153,16 +282,55 @@ class UtilStrByteMode {
|
|
|
153
282
|
}
|
|
154
283
|
return strRet;
|
|
155
284
|
}
|
|
285
|
+
/// <summary> In-String Search
|
|
286
|
+
/// Returns a number that represents the first position (byte) of a
|
|
287
|
+
/// substring within a string.
|
|
288
|
+
///
|
|
289
|
+
/// </summary>
|
|
290
|
+
/// <param name="strTarget:">string (in Unicode)
|
|
291
|
+
/// </param>
|
|
292
|
+
/// <param name="strSearch:">string which will be the search argument in string
|
|
293
|
+
/// </param>
|
|
294
|
+
/// <returns> number, 0 if not found
|
|
295
|
+
///
|
|
296
|
+
/// Example: instrB("abXYc", "Y")
|
|
297
|
+
/// Where 'a', 'b' and 'c' are SBCS, and 'X' and 'Y' are DBCS, it returns
|
|
298
|
+
/// 5.
|
|
299
|
+
/// </returns>
|
|
156
300
|
static instrB(strTarget, strSearch) {
|
|
157
301
|
if (strSearch.length === 0) {
|
|
302
|
+
// nothing to look for
|
|
158
303
|
return 0;
|
|
159
304
|
}
|
|
160
305
|
let ofs = strTarget.indexOf(strSearch);
|
|
161
306
|
if (ofs < 0) {
|
|
307
|
+
// not found
|
|
162
308
|
return 0;
|
|
163
309
|
}
|
|
164
310
|
return UtilStrByteMode.lenB(strTarget.substr(0, ofs)) + 1;
|
|
165
311
|
}
|
|
312
|
+
/// <summary> Replace Substring Within a String (Byte Mode)
|
|
313
|
+
/// Replaces a substring within a string with another substring.
|
|
314
|
+
/// If a DBCS character is divided in two, it will be replace to a space.
|
|
315
|
+
///
|
|
316
|
+
/// </summary>
|
|
317
|
+
/// <param name="strTarget:">target string where the replacement will take place.
|
|
318
|
+
/// </param>
|
|
319
|
+
/// <param name="strOrigin:">string that provides the substring to be copied to
|
|
320
|
+
/// target.
|
|
321
|
+
/// </param>
|
|
322
|
+
/// <param name="ofs:">the first position (byte) in the target string that will
|
|
323
|
+
/// receive the substring from origin.
|
|
324
|
+
/// </param>
|
|
325
|
+
/// <param name="len:">the number of bytes that will be moved from origin to
|
|
326
|
+
/// target, starting from the leftmost character of origin.
|
|
327
|
+
/// </param>
|
|
328
|
+
/// <returns> string containing modified target string
|
|
329
|
+
///
|
|
330
|
+
/// Example: repB("abXYc", "de", 4, 2)
|
|
331
|
+
/// Where 'a', 'b', 'c', 'd' and 'e' are SBCS, and 'X' and 'Y' are DBCS,
|
|
332
|
+
/// it returns "ab de c".
|
|
333
|
+
/// </returns>
|
|
166
334
|
static repB(strTarget, strOrigin, ofs, len) {
|
|
167
335
|
let strbufAddingBuf = new StringBuilder();
|
|
168
336
|
if (ofs < 0) {
|
|
@@ -185,12 +353,33 @@ class UtilStrByteMode {
|
|
|
185
353
|
if (intRightLen > 0) {
|
|
186
354
|
strbufAddingBuf.Append(UtilStrByteMode.rightB(strTarget, intRightLen));
|
|
187
355
|
}
|
|
356
|
+
// add blanks to the end
|
|
188
357
|
intAddSpaceLen = len - UtilStrByteMode.lenB(strOrigin);
|
|
189
358
|
for (; intAddSpaceLen > 0; intAddSpaceLen--) {
|
|
190
359
|
strbufAddingBuf.Append(' ');
|
|
191
360
|
}
|
|
192
361
|
return strbufAddingBuf.ToString();
|
|
193
362
|
}
|
|
363
|
+
/// <summary> Replace Substring Within a String (Character Mode)
|
|
364
|
+
/// Replaces a substring within a string with another substring.
|
|
365
|
+
///
|
|
366
|
+
/// </summary>
|
|
367
|
+
/// <param name="strTarget:">target string where the replacement will take place.
|
|
368
|
+
/// </param>
|
|
369
|
+
/// <param name="strOrigin:">string that provides the substring to be copied to
|
|
370
|
+
/// target.
|
|
371
|
+
/// </param>
|
|
372
|
+
/// <param name="ofs:">the first position (character) in the target string that
|
|
373
|
+
/// will receive the substring from origin.
|
|
374
|
+
/// </param>
|
|
375
|
+
/// <param name="len:">the number of characters that will be moved from origin
|
|
376
|
+
/// to target, starting from the leftmost character of origin.
|
|
377
|
+
/// </param>
|
|
378
|
+
/// <returns> string containing modified target string
|
|
379
|
+
///
|
|
380
|
+
/// Example: repB("abXYc", "de", 4, 2)
|
|
381
|
+
/// Whether each character is SBCS or DBCS, it returns "abXde".
|
|
382
|
+
/// </returns>
|
|
194
383
|
static repC(strTarget, strOrigin, ofs, len) {
|
|
195
384
|
let strbufAddingBuf = new StringBuilder();
|
|
196
385
|
if (ofs < 0) {
|
|
@@ -205,6 +394,7 @@ class UtilStrByteMode {
|
|
|
205
394
|
len = 0;
|
|
206
395
|
}
|
|
207
396
|
strbufAddingBuf.Append(strTarget.substr(0, ofs));
|
|
397
|
+
// add blanks between strTarget and strOrigin
|
|
208
398
|
let intAddSpaceLen = ofs - strTarget.length;
|
|
209
399
|
for (; intAddSpaceLen > 0; intAddSpaceLen--)
|
|
210
400
|
strbufAddingBuf.Append(' ');
|
|
@@ -218,9 +408,18 @@ class UtilStrByteMode {
|
|
|
218
408
|
}
|
|
219
409
|
return strbufAddingBuf.ToString();
|
|
220
410
|
}
|
|
411
|
+
/// <summary> Checks whether a character is 1 byte (halfwidth) or not (fullwidth)
|
|
412
|
+
/// Returns true if the character is represented by 1 byte in non-Unicode
|
|
413
|
+
/// encoding.
|
|
414
|
+
/// </summary>
|
|
415
|
+
/// <param name="letter:">a character to be checked.
|
|
416
|
+
/// </param>
|
|
417
|
+
/// <returns> true if the character is halfwidth (SBCS), or false if it is
|
|
418
|
+
/// fullwidth (DBCS).
|
|
419
|
+
/// </returns>
|
|
221
420
|
static isHalfWidth(str) {
|
|
222
421
|
let letter = str.charCodeAt(0);
|
|
223
|
-
if (32 <= letter && letter <= 126) {
|
|
422
|
+
if (32 <= /*' '*/ letter && letter <= 126 /*'~'*/) {
|
|
224
423
|
return true;
|
|
225
424
|
}
|
|
226
425
|
else {
|
|
@@ -230,18 +429,33 @@ class UtilStrByteMode {
|
|
|
230
429
|
}
|
|
231
430
|
return false;
|
|
232
431
|
}
|
|
432
|
+
/// <summary> Checks whether a character is halfwidth digit letter
|
|
433
|
+
/// Do not use "Character.isDigit" which cannot distinguish between
|
|
434
|
+
/// halfwidth digit letter(SBCS) and fullwidth difit letter(DBCS).
|
|
435
|
+
/// </summary>
|
|
436
|
+
/// <param name="letter:">a character to be checked.
|
|
437
|
+
/// </param>
|
|
438
|
+
/// <returns> true if the character is halfwidth digit letter, or
|
|
439
|
+
/// false if it is DBCS or not digit letter.
|
|
440
|
+
/// </returns>
|
|
233
441
|
static isDigit(letter) {
|
|
234
|
-
return 48 <= letter.charCodeAt(0) && letter.charCodeAt(0) <= 57
|
|
235
|
-
}
|
|
442
|
+
return 48 <= /*'0'*/ letter.charCodeAt(0) && letter.charCodeAt(0) <= 57 /*'9'*/;
|
|
443
|
+
}
|
|
444
|
+
/// <summary>Checks whether a character is one of those supported for # Alpha Mask</summary>
|
|
445
|
+
/// <param name="letter:">a character to be checked.
|
|
446
|
+
/// </param>
|
|
447
|
+
/// <returns> true if the character is halfwidth digit letter, or
|
|
448
|
+
/// false if it is DBCS or not digit letter.
|
|
449
|
+
/// </returns>
|
|
236
450
|
static asNumeric(letter) {
|
|
237
451
|
let result;
|
|
238
452
|
switch (letter.charCodeAt(0)) {
|
|
239
|
-
case 42:
|
|
240
|
-
case 43:
|
|
241
|
-
case 44:
|
|
242
|
-
case 45:
|
|
243
|
-
case 46:
|
|
244
|
-
case 47:
|
|
453
|
+
case 42: /*'*'*/
|
|
454
|
+
case 43: /*'+'*/
|
|
455
|
+
case 44: /*','*/
|
|
456
|
+
case 45: /*'-'*/
|
|
457
|
+
case 46: /*'.'*/
|
|
458
|
+
case 47: /*'/'*/
|
|
245
459
|
result = true;
|
|
246
460
|
break;
|
|
247
461
|
default:
|
|
@@ -250,12 +464,47 @@ class UtilStrByteMode {
|
|
|
250
464
|
}
|
|
251
465
|
return result;
|
|
252
466
|
}
|
|
467
|
+
/// <summary> Converts a position for the 1st string (Source) to a position for
|
|
468
|
+
/// the 2nd string (Dest).
|
|
469
|
+
/// If a double byte character exists in the strings, the position for the
|
|
470
|
+
/// Source could be different from the position for the Dest.
|
|
471
|
+
/// (DBCS Support)
|
|
472
|
+
///
|
|
473
|
+
/// </summary>
|
|
474
|
+
/// <param name="strSource:">Source string
|
|
475
|
+
/// </param>
|
|
476
|
+
/// <param name="strDest:">Dest string
|
|
477
|
+
/// </param>
|
|
478
|
+
/// <param name="pos:">position in the Source string
|
|
479
|
+
/// </param>
|
|
480
|
+
/// <param name="isAdvance:">advance or retreat the ret pos if a DBCS char is split
|
|
481
|
+
/// </param>
|
|
482
|
+
/// <returns> position in the Dest string
|
|
483
|
+
///
|
|
484
|
+
/// Example: convPos("abcYZ", "YZabc", 4)
|
|
485
|
+
/// It returns 4, if the all characters in the strings are SBCS.
|
|
486
|
+
///
|
|
487
|
+
/// If 'a', 'b' and 'c' are SBCS, and 'Y' and 'Z' are DBCS, it
|
|
488
|
+
/// returns 3.
|
|
489
|
+
/// pos
|
|
490
|
+
/// Unicode index 0 1 2 3 [4]
|
|
491
|
+
/// +-------------+
|
|
492
|
+
/// Source string |a|b|c| Y | Z |
|
|
493
|
+
/// +-------------+
|
|
494
|
+
/// ANSI index 0 1 2 3 4[5]6
|
|
495
|
+
/// +-------------+
|
|
496
|
+
/// Dest string | Y | Z |a|b|c|
|
|
497
|
+
/// +-------------+
|
|
498
|
+
/// Unicode index 0 1 2[3]4
|
|
499
|
+
/// ret
|
|
500
|
+
/// </returns>
|
|
253
501
|
static convPos(strSource, strDest, pos, isAdvance) {
|
|
254
502
|
let retPos;
|
|
255
503
|
if (pos < 0)
|
|
256
504
|
return 0;
|
|
257
505
|
if (pos > strSource.length)
|
|
258
506
|
pos = strSource.length;
|
|
507
|
+
// add blanks to the Dest string if it is shorter than the Src string
|
|
259
508
|
let diffLen = UtilStrByteMode.lenB(strSource) - UtilStrByteMode.lenB(strDest);
|
|
260
509
|
if (diffLen > 0) {
|
|
261
510
|
let stringBuilder = new StringBuilder(strDest);
|
|
@@ -266,11 +515,23 @@ class UtilStrByteMode {
|
|
|
266
515
|
let byteSource = UtilStrByteMode.Encoding.GetBytes(strSource.substr(0, pos));
|
|
267
516
|
let strLeftB = UtilStrByteMode.leftB(strDest, byteSource.length);
|
|
268
517
|
retPos = strLeftB.length;
|
|
269
|
-
if (!isAdvance && retPos > 0 && strLeftB.charCodeAt(retPos - 1) === 32 && strDest.charCodeAt(retPos - 1) !== 32) {
|
|
518
|
+
if (!isAdvance && retPos > 0 && strLeftB.charCodeAt(retPos - 1) === 32 /*' '*/ && strDest.charCodeAt(retPos - 1) !== 32 /*' '*/) {
|
|
270
519
|
retPos = retPos - 1;
|
|
271
520
|
}
|
|
272
521
|
return retPos;
|
|
273
522
|
}
|
|
523
|
+
/// <summary> return the number of characters of picture which corresponds to
|
|
524
|
+
/// given string.
|
|
525
|
+
/// </summary>
|
|
526
|
+
/// <param name="str:">given string
|
|
527
|
+
/// </param>
|
|
528
|
+
/// <param name="picture:">picture
|
|
529
|
+
/// </param>
|
|
530
|
+
/// <returns> minimal length of picture
|
|
531
|
+
/// Example: getMinLenPicture("ZZ20/11/", "JJJJYY/MM/DD") [ZZ is DBCS]
|
|
532
|
+
/// It returns 10.
|
|
533
|
+
/// </returns>
|
|
534
|
+
/// (DBCS Support)
|
|
274
535
|
static getMinLenPicture(str, picture) {
|
|
275
536
|
let len = 0;
|
|
276
537
|
if (UtilStrByteMode.lenB(picture) - UtilStrByteMode.lenB(str) > 0) {
|
|
@@ -280,6 +541,18 @@ class UtilStrByteMode {
|
|
|
280
541
|
len = picture.length;
|
|
281
542
|
return len;
|
|
282
543
|
}
|
|
544
|
+
/// <summary>
|
|
545
|
+
/// </summary> Compares two specified strings in the DBCS sort order and returns an integer
|
|
546
|
+
/// that indicates their relative position.
|
|
547
|
+
/// <param name="str1:">The first string to compare.
|
|
548
|
+
/// </param>
|
|
549
|
+
/// <param name="str2:">The second string to compare.
|
|
550
|
+
/// </param>
|
|
551
|
+
/// <returns>an integer that indicates the lexical relationship between the two strings.
|
|
552
|
+
/// -1: str1 is less than str2.
|
|
553
|
+
/// 0: str1 equals str2.
|
|
554
|
+
/// 1: str1 is greater than str2.
|
|
555
|
+
/// </returns>
|
|
283
556
|
static strcmp(str1, str2) {
|
|
284
557
|
let array1 = UtilStrByteMode.Encoding.GetBytes(str1);
|
|
285
558
|
let array2 = UtilStrByteMode.Encoding.GetBytes(str2);
|
|
@@ -300,19 +573,28 @@ class UtilStrByteMode {
|
|
|
300
573
|
}
|
|
301
574
|
}
|
|
302
575
|
|
|
576
|
+
//@dynamic
|
|
303
577
|
class Rtf_SYMBOL {
|
|
304
578
|
szKeyword = null;
|
|
579
|
+
/* RTF keyword */
|
|
305
580
|
kwd = null;
|
|
581
|
+
/* base action to take */
|
|
306
582
|
idxInRgprop = null;
|
|
583
|
+
/* index into property table if kwd == kwdProp */
|
|
584
|
+
/* index into destination table if kwd == kwdDest */
|
|
585
|
+
/* character to print if kwd == kwdChar */
|
|
307
586
|
constructor(keyWord, kwd, idxInRgprop) {
|
|
308
587
|
this.szKeyword = keyWord;
|
|
309
588
|
this.kwd = kwd;
|
|
310
589
|
this.idxInRgprop = idxInRgprop;
|
|
311
590
|
}
|
|
312
591
|
}
|
|
592
|
+
// @dynamic
|
|
313
593
|
class Rtf_PROP {
|
|
314
594
|
actn = null;
|
|
595
|
+
/* size of value */
|
|
315
596
|
prop = null;
|
|
597
|
+
/* structure containing value */
|
|
316
598
|
constructor(actn, prop) {
|
|
317
599
|
this.actn = actn;
|
|
318
600
|
this.prop = prop;
|
|
@@ -359,6 +641,7 @@ var Rtf_IDEST;
|
|
|
359
641
|
Rtf_IDEST[Rtf_IDEST["COLOR"] = 1] = "COLOR";
|
|
360
642
|
Rtf_IDEST[Rtf_IDEST["SKIP"] = 2] = "SKIP";
|
|
361
643
|
})(Rtf_IDEST || (Rtf_IDEST = {}));
|
|
644
|
+
/* types of properties */
|
|
362
645
|
var Rtf_IPROP;
|
|
363
646
|
(function (Rtf_IPROP) {
|
|
364
647
|
Rtf_IPROP[Rtf_IPROP["BOLD"] = 0] = "BOLD";
|
|
@@ -395,6 +678,7 @@ var Rtf_IPROP;
|
|
|
395
678
|
Rtf_IPROP[Rtf_IPROP["XA_BULLET"] = 31] = "XA_BULLET";
|
|
396
679
|
Rtf_IPROP[Rtf_IPROP["MAX"] = 32] = "MAX";
|
|
397
680
|
})(Rtf_IPROP || (Rtf_IPROP = {}));
|
|
681
|
+
/* Rtf Destination State */
|
|
398
682
|
var Rtf_RDS;
|
|
399
683
|
(function (Rtf_RDS) {
|
|
400
684
|
Rtf_RDS[Rtf_RDS["NORM"] = 0] = "NORM";
|
|
@@ -414,6 +698,15 @@ var Rtf_ErrorRtf;
|
|
|
414
698
|
Rtf_ErrorRtf[Rtf_ErrorRtf["END_OF_FILE"] = 7] = "END_OF_FILE";
|
|
415
699
|
Rtf_ErrorRtf[Rtf_ErrorRtf["BUFFER_TOO_SMALL"] = 8] = "BUFFER_TOO_SMALL";
|
|
416
700
|
})(Rtf_ErrorRtf || (Rtf_ErrorRtf = {}));
|
|
701
|
+
// TODO :
|
|
702
|
+
// Rtf_RtfChar should actually be enum.
|
|
703
|
+
// But computed string values are not allowed to be defined in enum.
|
|
704
|
+
// So, we cannot have String.fromCharCode(XXX).
|
|
705
|
+
// We have 2 options:
|
|
706
|
+
// 1. Convert this enum into a class with all static readonly items.
|
|
707
|
+
// 2. Keep it as enum with numeric values (char codes).
|
|
708
|
+
// Going with #1 now, since @2 makes the code ugly.
|
|
709
|
+
// Will evalaute later if required.
|
|
417
710
|
class Rtf_RtfChar {
|
|
418
711
|
static CR = String.fromCharCode(0x0d);
|
|
419
712
|
static LF = String.fromCharCode(0x0A);
|
|
@@ -451,6 +744,7 @@ class Rtf {
|
|
|
451
744
|
_codePageTable = new Hashtable();
|
|
452
745
|
static RTF_PREFIX = "{\\rtf";
|
|
453
746
|
static CHAR_PAR = "par";
|
|
747
|
+
/* Property descriptions */
|
|
454
748
|
static rgprop = [
|
|
455
749
|
new Rtf_PROP(Rtf_ACTN.BYTE, Rtf_PROPTYPE.CHP), new Rtf_PROP(Rtf_ACTN.BYTE, Rtf_PROPTYPE.CHP),
|
|
456
750
|
new Rtf_PROP(Rtf_ACTN.BYTE, Rtf_PROPTYPE.CHP), new Rtf_PROP(Rtf_ACTN.BYTE, Rtf_PROPTYPE.CHP),
|
|
@@ -468,6 +762,7 @@ class Rtf {
|
|
|
468
762
|
new Rtf_PROP(Rtf_ACTN.BYTE, Rtf_PROPTYPE.PAP), new Rtf_PROP(Rtf_ACTN.SPEC, Rtf_PROPTYPE.PAP),
|
|
469
763
|
new Rtf_PROP(Rtf_ACTN.SPEC, Rtf_PROPTYPE.CHP), new Rtf_PROP(Rtf_ACTN.SPEC, Rtf_PROPTYPE.SEP)
|
|
470
764
|
];
|
|
765
|
+
/* Keyword descriptions */
|
|
471
766
|
static rgsymRtf = [
|
|
472
767
|
new Rtf_SYMBOL("b", Rtf_KWD.PROP, Rtf_IPROP.BOLD), new Rtf_SYMBOL("ul", Rtf_KWD.PROP, Rtf_IPROP.UNDERLINE),
|
|
473
768
|
new Rtf_SYMBOL("i", Rtf_KWD.PROP, Rtf_IPROP.ITALIC), new Rtf_SYMBOL("li", Rtf_KWD.PROP, Rtf_IPROP.LEFT_IND),
|
|
@@ -514,6 +809,8 @@ class Rtf {
|
|
|
514
809
|
new Rtf_SYMBOL("title", Rtf_KWD.DEST, Rtf_IDEST.SKIP), new Rtf_SYMBOL("txe", Rtf_KWD.DEST, Rtf_IDEST.SKIP),
|
|
515
810
|
new Rtf_SYMBOL("xe", Rtf_KWD.DEST, Rtf_IDEST.SKIP)
|
|
516
811
|
];
|
|
812
|
+
/// <summary> Constructor
|
|
813
|
+
/// </summary>
|
|
517
814
|
constructor() {
|
|
518
815
|
this._stack = new Stack();
|
|
519
816
|
this._group = 0;
|
|
@@ -529,6 +826,13 @@ class Rtf {
|
|
|
529
826
|
this.setCodePageTable();
|
|
530
827
|
}
|
|
531
828
|
}
|
|
829
|
+
/// <summary> Checks if the blob has a Rtf data or not
|
|
830
|
+
///
|
|
831
|
+
/// </summary>
|
|
832
|
+
/// <param name="str">
|
|
833
|
+
/// </param>
|
|
834
|
+
/// <returns>
|
|
835
|
+
/// </returns>
|
|
532
836
|
static isRtf(str) {
|
|
533
837
|
let isRtf = false;
|
|
534
838
|
if (str !== null && str.startsWith(this.RTF_PREFIX)) {
|
|
@@ -536,6 +840,17 @@ class Rtf {
|
|
|
536
840
|
}
|
|
537
841
|
return isRtf;
|
|
538
842
|
}
|
|
843
|
+
/// <summary> Converts Rtf Text to Plain Text
|
|
844
|
+
/// Step 1: Isolate RTF keywords and send them to ParseKeyword; Push and pop state at the start and end of
|
|
845
|
+
/// RTF groups Send text to ParseChar for further processing.
|
|
846
|
+
///
|
|
847
|
+
/// </summary>
|
|
848
|
+
/// <param name="rtfTxt">
|
|
849
|
+
/// </param>
|
|
850
|
+
/// <param name="outputTxt">
|
|
851
|
+
/// </param>
|
|
852
|
+
/// <returns>
|
|
853
|
+
/// </returns>
|
|
539
854
|
toTxt(rtfTxt, outputTxt) {
|
|
540
855
|
let cNibble = 2;
|
|
541
856
|
let b = 0;
|
|
@@ -561,6 +876,7 @@ class Rtf {
|
|
|
561
876
|
this._index++;
|
|
562
877
|
if (this._group < 0)
|
|
563
878
|
return Rtf_ErrorRtf.STACK_UNDERFLOW;
|
|
879
|
+
/* if we're parsing binary data, handle it directly */
|
|
564
880
|
if (this._internalState === Rtf_RIS.BIN) {
|
|
565
881
|
if ((ec = this.ParseChar(blobChar, outputTxt)) !== Rtf_ErrorRtf.OK)
|
|
566
882
|
return ec;
|
|
@@ -583,16 +899,22 @@ class Rtf {
|
|
|
583
899
|
return ec;
|
|
584
900
|
break;
|
|
585
901
|
case Rtf_RtfChar.LF:
|
|
586
|
-
case Rtf_RtfChar.CR:
|
|
902
|
+
case Rtf_RtfChar.CR: /* cr and lf are noise characters... */
|
|
587
903
|
if (this._processCrlfSpecial) {
|
|
904
|
+
/* Once we reach the 0x0a while ProcessCRLFSpecial_, reset the ProcessCRLFSpecial_ */
|
|
588
905
|
if (blobChar === Rtf_RtfChar.LF) {
|
|
589
906
|
this._processCrlfSpecial = false;
|
|
590
907
|
}
|
|
591
908
|
}
|
|
592
909
|
else {
|
|
910
|
+
/*---------------------------------------------------------------*/
|
|
911
|
+
/* skip new lines coming only from the RTF header 1/1/98 - #2390 */
|
|
912
|
+
/*---------------------------------------------------------------*/
|
|
913
|
+
/* Skip the LF (0x0a) if we are not in the ProcessCRLFSpecial_ */
|
|
593
914
|
if (blobChar === Rtf_RtfChar.LF || (blobChar === Rtf_RtfChar.CR && skipNewline && !this._outputOnce))
|
|
594
915
|
break;
|
|
595
916
|
}
|
|
917
|
+
/* falls through */
|
|
596
918
|
default:
|
|
597
919
|
if (blobChar !== Rtf_RtfChar.CR)
|
|
598
920
|
skipNewline = false;
|
|
@@ -606,6 +928,7 @@ class Rtf {
|
|
|
606
928
|
this._internalState = Rtf_RIS.NORM;
|
|
607
929
|
}
|
|
608
930
|
else {
|
|
931
|
+
/* parsing hex data */
|
|
609
932
|
if (this._internalState !== Rtf_RIS.HEX)
|
|
610
933
|
return Rtf_ErrorRtf.ASSERTION;
|
|
611
934
|
b = b << 4;
|
|
@@ -627,18 +950,22 @@ class Rtf {
|
|
|
627
950
|
if (cNibble === 0) {
|
|
628
951
|
if (UtilStrByteMode.isLocaleDefLangDBCS()) {
|
|
629
952
|
charset = this.getCharset(this._fontNum);
|
|
953
|
+
// leading byte of a double-byte character
|
|
630
954
|
if (!skipParseChar && Rtf.is1stByte(b, charset)) {
|
|
631
955
|
dbcsBytes[0] = b;
|
|
632
956
|
dbcsBytes[1] = 0;
|
|
633
957
|
skipParseChar = true;
|
|
634
958
|
}
|
|
635
959
|
else {
|
|
960
|
+
// trailing byte of a double-byte character
|
|
636
961
|
if (skipParseChar && Rtf.is2ndByte(b, charset))
|
|
637
962
|
dbcsBytes[1] = b;
|
|
963
|
+
// single-byte character
|
|
638
964
|
else {
|
|
639
965
|
dbcsBytes[0] = b;
|
|
640
966
|
dbcsBytes[1] = 0;
|
|
641
967
|
}
|
|
968
|
+
// convert DBCS to Unicode
|
|
642
969
|
codePage = this.getCodePage(charset);
|
|
643
970
|
let workStr = Encoding.GetEncoding(codePage).GetString(dbcsBytes, 0, 2);
|
|
644
971
|
b = workStr.charCodeAt(0);
|
|
@@ -654,19 +981,36 @@ class Rtf {
|
|
|
654
981
|
this._internalState = Rtf_RIS.NORM;
|
|
655
982
|
}
|
|
656
983
|
}
|
|
984
|
+
/* end else (ris != risNorm) */
|
|
657
985
|
break;
|
|
658
986
|
}
|
|
987
|
+
/* switch */
|
|
659
988
|
}
|
|
989
|
+
/* else (ris != risBin) */
|
|
660
990
|
}
|
|
991
|
+
/* while */
|
|
661
992
|
if (this._group < 0)
|
|
662
993
|
return Rtf_ErrorRtf.STACK_UNDERFLOW;
|
|
663
994
|
if (this._group > 0)
|
|
664
995
|
return Rtf_ErrorRtf.UNMATCHED_BRACE;
|
|
996
|
+
/*-------------------------------------------------------------------*/
|
|
997
|
+
/* Eliminate suffix of carrige return + line feed */
|
|
998
|
+
/* (Check last characters - just in case format is not the expected) */
|
|
999
|
+
/*-------------------------------------------------------------------*/
|
|
665
1000
|
currPos = outputTxt.Length;
|
|
666
1001
|
if (currPos >= 3 && (outputTxt.get_Item(currPos - 3) === Rtf_RtfChar.CR && outputTxt.get_Item(currPos - 2) === Rtf_RtfChar.LF && outputTxt.get_Item(currPos - 1) === Rtf_RtfChar.CR || outputTxt.get_Item(currPos - 3) === Rtf_RtfChar.LF && outputTxt.get_Item(currPos - 2) === Rtf_RtfChar.CR && outputTxt.get_Item(currPos - 1) === Rtf_RtfChar.CR))
|
|
667
1002
|
outputTxt.Remove(currPos - 3, 3);
|
|
668
1003
|
return Rtf_ErrorRtf.OK;
|
|
669
1004
|
}
|
|
1005
|
+
/// <summary> Route the character to the appropriate destination stream.
|
|
1006
|
+
///
|
|
1007
|
+
/// </summary>
|
|
1008
|
+
/// <param name="ch">
|
|
1009
|
+
/// </param>
|
|
1010
|
+
/// <param name="outputTxt">
|
|
1011
|
+
/// </param>
|
|
1012
|
+
/// <returns>
|
|
1013
|
+
/// </returns>
|
|
670
1014
|
ParseChar(ch, outputTxt) {
|
|
671
1015
|
let ret = Rtf_ErrorRtf.OK;
|
|
672
1016
|
if (this._internalState === Rtf_RIS.BIN && --this._cbBin <= 0) {
|
|
@@ -674,14 +1018,28 @@ class Rtf {
|
|
|
674
1018
|
}
|
|
675
1019
|
if (this._destState === Rtf_RDS.SKIP) {
|
|
676
1020
|
}
|
|
1021
|
+
/* Toss this character. */
|
|
677
1022
|
else if (this._destState === Rtf_RDS.NORM) {
|
|
1023
|
+
/* Output a character. Properties are valid at this point. */
|
|
678
1024
|
ret = this.PrintChar(ch, outputTxt);
|
|
679
1025
|
}
|
|
680
1026
|
else {
|
|
1027
|
+
/* handle other destinations.... */
|
|
681
1028
|
}
|
|
682
1029
|
return ret;
|
|
683
1030
|
}
|
|
1031
|
+
/// <summary> Send a character to the output file.
|
|
1032
|
+
///
|
|
1033
|
+
/// </summary>
|
|
1034
|
+
/// <param name="ch">
|
|
1035
|
+
/// </param>
|
|
1036
|
+
/// <param name="outputTxt">
|
|
1037
|
+
/// </param>
|
|
1038
|
+
/// <returns>
|
|
1039
|
+
/// </returns>
|
|
684
1040
|
PrintChar(ch, outputTxt) {
|
|
1041
|
+
/* Allow carrige return + line feed in text, but remove bullet sign */
|
|
1042
|
+
/*------------------------------------------------------------------*/
|
|
685
1043
|
if ((ch >= ' ' || ch === Rtf_RtfChar.CR || ch === Rtf_RtfChar.LF) && ch !== String.fromCharCode(183)) {
|
|
686
1044
|
outputTxt.Append(ch);
|
|
687
1045
|
}
|
|
@@ -690,6 +1048,11 @@ class Rtf {
|
|
|
690
1048
|
}
|
|
691
1049
|
return Rtf_ErrorRtf.OK;
|
|
692
1050
|
}
|
|
1051
|
+
/// <summary> Save relevant info on a linked list of SAVE structures.
|
|
1052
|
+
///
|
|
1053
|
+
/// </summary>
|
|
1054
|
+
/// <returns>
|
|
1055
|
+
/// </returns>
|
|
693
1056
|
PushState() {
|
|
694
1057
|
let stackSave = new Rtf_StackSave();
|
|
695
1058
|
if (stackSave === null) {
|
|
@@ -702,6 +1065,11 @@ class Rtf {
|
|
|
702
1065
|
this._group++;
|
|
703
1066
|
return Rtf_ErrorRtf.OK;
|
|
704
1067
|
}
|
|
1068
|
+
/// <summary> Always restore relevant info from the top of the SAVE list.
|
|
1069
|
+
///
|
|
1070
|
+
/// </summary>
|
|
1071
|
+
/// <returns>
|
|
1072
|
+
/// </returns>
|
|
705
1073
|
PopState() {
|
|
706
1074
|
let savedPop = this._stack.pop();
|
|
707
1075
|
if (savedPop === null) {
|
|
@@ -712,6 +1080,15 @@ class Rtf {
|
|
|
712
1080
|
this._group--;
|
|
713
1081
|
return Rtf_ErrorRtf.OK;
|
|
714
1082
|
}
|
|
1083
|
+
/// <summary> Step 2: get a control word (and its associated value) and call TranslateKeyword to dispatch the control.
|
|
1084
|
+
///
|
|
1085
|
+
/// </summary>
|
|
1086
|
+
/// <param name="rtfTxt">
|
|
1087
|
+
/// </param>
|
|
1088
|
+
/// <param name="outputTxt">
|
|
1089
|
+
/// </param>
|
|
1090
|
+
/// <returns>
|
|
1091
|
+
/// </returns>
|
|
715
1092
|
ParseKeyword(rtfTxt, outputTxt) {
|
|
716
1093
|
let ch;
|
|
717
1094
|
let fNeg = false;
|
|
@@ -720,6 +1097,7 @@ class Rtf {
|
|
|
720
1097
|
if ((ch = rtfTxt[this._index++]) === String.fromCharCode(0)) {
|
|
721
1098
|
return Rtf_ErrorRtf.END_OF_FILE;
|
|
722
1099
|
}
|
|
1100
|
+
/* a control symbol; no delimiter. */
|
|
723
1101
|
if (!NChar.IsLetter(ch)) {
|
|
724
1102
|
szKeyword = szKeyword + ch;
|
|
725
1103
|
return this.TranslateKeyword(szKeyword, outputTxt);
|
|
@@ -741,6 +1119,13 @@ class Rtf {
|
|
|
741
1119
|
if (ch !== ' ')
|
|
742
1120
|
this._index--;
|
|
743
1121
|
if (szKeyword === Rtf.CHAR_PAR) {
|
|
1122
|
+
/* if we get a RTF sequence of \par[0xd][0xa], ie a \par kwd followed */
|
|
1123
|
+
/* immidiately by the CR and LF, then ignore the \par kwd. otherwise */
|
|
1124
|
+
/* we will translate the \par - which translates to a LF (0xa) and also */
|
|
1125
|
+
/* the following 0x0d is translated to 0x0a, thus resulting in TWO LF's */
|
|
1126
|
+
/* being inserted instead of just one LF. So by skipping [\par] and */
|
|
1127
|
+
/* translating only the [0xd 0xa] will result in only one LF appearing */
|
|
1128
|
+
/* - which is the desired behaviour */
|
|
744
1129
|
if (rtfTxt[this._index] === Rtf_RtfChar.CR && rtfTxt[this._index + 1] === Rtf_RtfChar.LF)
|
|
745
1130
|
this._processCrlfSpecial = true;
|
|
746
1131
|
}
|
|
@@ -751,22 +1136,37 @@ class Rtf {
|
|
|
751
1136
|
return this.TranslateKeyword(szKeyword, outputTxt);
|
|
752
1137
|
}
|
|
753
1138
|
}
|
|
1139
|
+
/// <summary> Step 3. Search rgsymRtf for szKeyword and evaluate it appropriately.
|
|
1140
|
+
///
|
|
1141
|
+
/// </summary>
|
|
1142
|
+
/// <param name="szKeyword">
|
|
1143
|
+
/// </param>
|
|
1144
|
+
/// <param name="outputTxt">
|
|
1145
|
+
/// </param>
|
|
1146
|
+
/// <returns>
|
|
1147
|
+
/// </returns>
|
|
754
1148
|
TranslateKeyword(szKeyword, outputTxt) {
|
|
755
1149
|
let result = Rtf_ErrorRtf.OK;
|
|
756
1150
|
let isym;
|
|
1151
|
+
/* search for szKeyword in rgsymRtf */
|
|
757
1152
|
for (isym = 0; isym < Rtf.rgsymRtf.length; isym++) {
|
|
758
1153
|
if (szKeyword === Rtf.rgsymRtf[isym].szKeyword) {
|
|
759
1154
|
break;
|
|
760
1155
|
}
|
|
761
1156
|
}
|
|
1157
|
+
/* control word not found */
|
|
762
1158
|
if (isym === Rtf.rgsymRtf.length) {
|
|
763
1159
|
if (this._skipDestIfUnk) {
|
|
1160
|
+
/* if this is a new destination */
|
|
764
1161
|
this._destState = Rtf_RDS.SKIP;
|
|
1162
|
+
/* skip the destination */
|
|
765
1163
|
}
|
|
1164
|
+
/* else just discard it */
|
|
766
1165
|
this._skipDestIfUnk = false;
|
|
767
1166
|
}
|
|
768
1167
|
else {
|
|
769
1168
|
result = Rtf_ErrorRtf.BAD_TABLE;
|
|
1169
|
+
/* found it! use kwd and idxInRgprop to determine what to do with it. */
|
|
770
1170
|
this._skipDestIfUnk = false;
|
|
771
1171
|
if (Rtf.rgsymRtf[isym].kwd === Rtf_KWD.PROP) {
|
|
772
1172
|
result = this.validateProp(Rtf.rgsymRtf[isym].idxInRgprop);
|
|
@@ -783,11 +1183,21 @@ class Rtf {
|
|
|
783
1183
|
}
|
|
784
1184
|
return result;
|
|
785
1185
|
}
|
|
1186
|
+
/// <summary> Validate the property identified by _iprop_ to the value _val_.
|
|
1187
|
+
/// previously called Applypropchange
|
|
1188
|
+
/// </summary>
|
|
1189
|
+
/// <param name="iprop">
|
|
1190
|
+
/// </param>
|
|
1191
|
+
/// <returns>
|
|
1192
|
+
/// </returns>
|
|
786
1193
|
validateProp(iprop) {
|
|
787
1194
|
let ret = Rtf_ErrorRtf.OK;
|
|
788
1195
|
if (this._destState === Rtf_RDS.SKIP) {
|
|
1196
|
+
/* If we're skipping text, */
|
|
789
1197
|
return ret;
|
|
1198
|
+
/* don't do anything. */
|
|
790
1199
|
}
|
|
1200
|
+
/* validate prop */
|
|
791
1201
|
if (Rtf.rgprop[iprop].prop !== Rtf_PROPTYPE.DOP && Rtf.rgprop[iprop].prop !== Rtf_PROPTYPE.SEP &&
|
|
792
1202
|
Rtf.rgprop[iprop].prop !== Rtf_PROPTYPE.PAP && Rtf.rgprop[iprop].prop !== Rtf_PROPTYPE.CHP &&
|
|
793
1203
|
Rtf.rgprop[iprop].actn !== Rtf_ACTN.SPEC) {
|
|
@@ -798,18 +1208,35 @@ class Rtf {
|
|
|
798
1208
|
}
|
|
799
1209
|
return ret;
|
|
800
1210
|
}
|
|
1211
|
+
/// <summary> Change to the destination state.
|
|
1212
|
+
/// previously called ChangeDest
|
|
1213
|
+
/// </summary>
|
|
1214
|
+
/// <returns>
|
|
1215
|
+
/// </returns>
|
|
801
1216
|
changeDestState() {
|
|
802
1217
|
if (this._destState === Rtf_RDS.SKIP) {
|
|
1218
|
+
/* if we're skipping text, */
|
|
803
1219
|
return Rtf_ErrorRtf.OK;
|
|
1220
|
+
/* don't do anything */
|
|
804
1221
|
}
|
|
805
1222
|
this._destState = Rtf_RDS.SKIP;
|
|
1223
|
+
/* when in doubt, skip it... */
|
|
806
1224
|
return Rtf_ErrorRtf.OK;
|
|
807
1225
|
}
|
|
1226
|
+
/// <summary> Evaluate an RTF control that needs special processing.
|
|
1227
|
+
///
|
|
1228
|
+
/// </summary>
|
|
1229
|
+
/// <param name="ipfn">
|
|
1230
|
+
/// </param>
|
|
1231
|
+
/// <returns>
|
|
1232
|
+
/// </returns>
|
|
808
1233
|
ParseSpecialKeyword(ipfn) {
|
|
809
1234
|
let ret = Rtf_ErrorRtf.OK;
|
|
810
1235
|
if (!UtilStrByteMode.isLocaleDefLangDBCS()) {
|
|
811
1236
|
if (this._destState === Rtf_RDS.SKIP && ipfn !== Rtf_IPFN.BIN) {
|
|
1237
|
+
/* if we're skipping, and it's not */
|
|
812
1238
|
return ret;
|
|
1239
|
+
/* the \bin keyword, ignore it. */
|
|
813
1240
|
}
|
|
814
1241
|
if (ipfn === Rtf_IPFN.FONT || ipfn === Rtf_IPFN.CHARSET || ipfn === Rtf_IPFN.UNICODE) {
|
|
815
1242
|
return ret;
|
|
@@ -863,6 +1290,15 @@ class Rtf {
|
|
|
863
1290
|
}
|
|
864
1291
|
return ret;
|
|
865
1292
|
}
|
|
1293
|
+
/// <summary> Checks if the byte is within the trailing byte range.
|
|
1294
|
+
///
|
|
1295
|
+
/// </summary>
|
|
1296
|
+
/// <param name="dbcsBytes">
|
|
1297
|
+
/// </param>
|
|
1298
|
+
/// <param name="charset">
|
|
1299
|
+
/// </param>
|
|
1300
|
+
/// <returns>
|
|
1301
|
+
/// </returns>
|
|
866
1302
|
static is2ndByte(dbcsBytes, charset) {
|
|
867
1303
|
let ret = false;
|
|
868
1304
|
if (dbcsBytes > 255)
|
|
@@ -881,21 +1317,35 @@ class Rtf {
|
|
|
881
1317
|
}
|
|
882
1318
|
return ret;
|
|
883
1319
|
}
|
|
1320
|
+
/// <summary> Create a hashtable of codepage associated with charset.
|
|
1321
|
+
///
|
|
1322
|
+
/// </summary>
|
|
1323
|
+
/// <param>
|
|
1324
|
+
/// <returns>
|
|
1325
|
+
/// </returns>
|
|
884
1326
|
setCodePageTable() {
|
|
885
|
-
|
|
886
|
-
this._codePageTable.set_Item(
|
|
887
|
-
this._codePageTable.set_Item(
|
|
888
|
-
this._codePageTable.set_Item(
|
|
889
|
-
this._codePageTable.set_Item(
|
|
890
|
-
this._codePageTable.set_Item(
|
|
891
|
-
this._codePageTable.set_Item(
|
|
892
|
-
this._codePageTable.set_Item(
|
|
893
|
-
this._codePageTable.set_Item(
|
|
894
|
-
this._codePageTable.set_Item(
|
|
895
|
-
this._codePageTable.set_Item(
|
|
896
|
-
this._codePageTable.set_Item(
|
|
897
|
-
this._codePageTable.set_Item(
|
|
898
|
-
|
|
1327
|
+
// add elements with key (charset) and value (codepage) into the table.
|
|
1328
|
+
this._codePageTable.set_Item(0, 1252); // ANSI_CHARSET
|
|
1329
|
+
this._codePageTable.set_Item(128, 932); // SHIFTJIS_CHARSET
|
|
1330
|
+
this._codePageTable.set_Item(129, 949); // HANGUL_CHARSET
|
|
1331
|
+
this._codePageTable.set_Item(134, 936); // GB2312_CHARSET
|
|
1332
|
+
this._codePageTable.set_Item(136, 950); // CHINESEBIG5_CHARSET
|
|
1333
|
+
this._codePageTable.set_Item(161, 1253); // GREEK_CHARSET
|
|
1334
|
+
this._codePageTable.set_Item(162, 1254); // TURKISH_CHARSET
|
|
1335
|
+
this._codePageTable.set_Item(177, 1255); // HEBREW_CHARSET
|
|
1336
|
+
this._codePageTable.set_Item(178, 1256); // ARABIC _CHARSET
|
|
1337
|
+
this._codePageTable.set_Item(186, 1257); // BALTIC_CHARSET
|
|
1338
|
+
this._codePageTable.set_Item(204, 1251); // RUSSIAN_CHARSET
|
|
1339
|
+
this._codePageTable.set_Item(222, 874); // THAI_CHARSET
|
|
1340
|
+
this._codePageTable.set_Item(238, 1250); // EASTEUROPE_CHARSET
|
|
1341
|
+
}
|
|
1342
|
+
/// <summary> Get codepage corresponding to the specified charset.
|
|
1343
|
+
///
|
|
1344
|
+
/// </summary>
|
|
1345
|
+
/// <param name="charset">
|
|
1346
|
+
/// </param>
|
|
1347
|
+
/// <returns>
|
|
1348
|
+
/// </returns>
|
|
899
1349
|
getCodePage(charset) {
|
|
900
1350
|
let codePage = 0;
|
|
901
1351
|
if (this._codePageTable.ContainsKey(charset)) {
|
|
@@ -903,6 +1353,13 @@ class Rtf {
|
|
|
903
1353
|
}
|
|
904
1354
|
return codePage;
|
|
905
1355
|
}
|
|
1356
|
+
/// <summary> Get charset corresponding to the specified font index.
|
|
1357
|
+
///
|
|
1358
|
+
/// </summary>
|
|
1359
|
+
/// <param name="font">
|
|
1360
|
+
/// </param>
|
|
1361
|
+
/// <returns>
|
|
1362
|
+
/// </returns>
|
|
906
1363
|
getCharset(font) {
|
|
907
1364
|
let charset = 0;
|
|
908
1365
|
if (this._charsetTable.ContainsKey(font)) {
|
|
@@ -923,6 +1380,7 @@ const HTML_2_SEQ = 4;
|
|
|
923
1380
|
const SEQ_2_STR = 5;
|
|
924
1381
|
class StrUtil {
|
|
925
1382
|
static _paddingSpaces = null;
|
|
1383
|
+
/// <summary> trim the end of the string</summary>
|
|
926
1384
|
static mem_trim(str, len) {
|
|
927
1385
|
let result;
|
|
928
1386
|
if (len > 0) {
|
|
@@ -957,6 +1415,15 @@ class StrUtil {
|
|
|
957
1415
|
}
|
|
958
1416
|
StrUtil.memcpy_1(dest, destCount, src, scrCountOrSrcCount, count);
|
|
959
1417
|
}
|
|
1418
|
+
/// <summary>
|
|
1419
|
+
/// copy part of string into another string, like memcpy of C, but 4 string only
|
|
1420
|
+
/// </summary>
|
|
1421
|
+
/// <param name = "dest">string</param>
|
|
1422
|
+
/// <param name = "destCount">of counter start from in destignation string</param>
|
|
1423
|
+
/// <param name = "src">string</param>
|
|
1424
|
+
/// <param name = "scrCount">of counter start from in source string</param>
|
|
1425
|
+
/// <param name = "count"></param>
|
|
1426
|
+
/// <returns> new value of destignation string</returns>
|
|
960
1427
|
static memcpy_0(dest, destCount, src, scrCount, count) {
|
|
961
1428
|
let stringBuilder = new StringBuilder(dest.substr(0, destCount));
|
|
962
1429
|
if (scrCount + count < src.length) {
|
|
@@ -983,6 +1450,14 @@ class StrUtil {
|
|
|
983
1450
|
}
|
|
984
1451
|
StrUtil.memset_1(dest, destCount, inVal, counter);
|
|
985
1452
|
}
|
|
1453
|
+
/// <summary>
|
|
1454
|
+
/// insert to string chars n times
|
|
1455
|
+
/// </summary>
|
|
1456
|
+
/// <param name = "dest">string</param>
|
|
1457
|
+
/// <param name = "destCount">of counter start from in destignation string to start insertion of char from</param>
|
|
1458
|
+
/// <param name = "inVal">2 insert</param>
|
|
1459
|
+
/// <param name = "counter">- number of times to insert the char</param>
|
|
1460
|
+
/// <returns> new value of destignation string</returns>
|
|
986
1461
|
static memset_0(dest, destCount, inVal, counter) {
|
|
987
1462
|
let first = new StringBuilder(dest.substr(0, destCount));
|
|
988
1463
|
while (counter > 0) {
|
|
@@ -1011,14 +1486,29 @@ class StrUtil {
|
|
|
1011
1486
|
}
|
|
1012
1487
|
return result;
|
|
1013
1488
|
}
|
|
1489
|
+
/*******************************/
|
|
1490
|
+
/// <summary>
|
|
1491
|
+
/// Reverses string values.
|
|
1492
|
+
/// </summary>
|
|
1493
|
+
/// <param name="text">The StringBuilder object containing the string to be reversed.</param>
|
|
1494
|
+
/// <returns>The reversed string contained in a StringBuilder object.</returns>
|
|
1014
1495
|
static ReverseString(text) {
|
|
1496
|
+
// TODO: use string.Reverse()
|
|
1015
1497
|
let array = NString.ToCharArray(text.ToString());
|
|
1016
1498
|
array.reverse();
|
|
1017
1499
|
return new StringBuilder(NString.FromChars(array));
|
|
1018
1500
|
}
|
|
1501
|
+
/// <summary> remove spaces from the right side of string</summary>
|
|
1502
|
+
/// <param name="str">the string to trim
|
|
1503
|
+
/// </param>
|
|
1019
1504
|
static rtrim(str) {
|
|
1020
1505
|
return StrUtil.rtrimWithNull(str, false);
|
|
1021
1506
|
}
|
|
1507
|
+
/// <summary> remove spaces and/or Null chars from the right side of string</summary>
|
|
1508
|
+
/// <param name="str">the string to trim
|
|
1509
|
+
/// </param>
|
|
1510
|
+
/// <param name="trimNullChars">Whether to remove NULL characters or not
|
|
1511
|
+
/// </param>
|
|
1022
1512
|
static rtrimWithNull(str, trimNullChars) {
|
|
1023
1513
|
let result;
|
|
1024
1514
|
if (typeof str === "undefined" || str === null || str.length === 0) {
|
|
@@ -1027,7 +1517,7 @@ class StrUtil {
|
|
|
1027
1517
|
else {
|
|
1028
1518
|
let idx = str.length - 1;
|
|
1029
1519
|
if (trimNullChars) {
|
|
1030
|
-
while (idx >= 0 && (str[idx] === ' ' || str[idx] === String.fromCharCode(0))) {
|
|
1520
|
+
while (idx >= 0 && (str[idx] === ' ' || str[idx] === String.fromCharCode(0) /*''*/)) {
|
|
1031
1521
|
idx = idx - 1;
|
|
1032
1522
|
}
|
|
1033
1523
|
}
|
|
@@ -1046,6 +1536,9 @@ class StrUtil {
|
|
|
1046
1536
|
}
|
|
1047
1537
|
return result;
|
|
1048
1538
|
}
|
|
1539
|
+
/// <summary> remove spaces from the left side of string</summary>
|
|
1540
|
+
/// <param name="str">the string to trim
|
|
1541
|
+
/// </param>
|
|
1049
1542
|
static ltrim(str) {
|
|
1050
1543
|
let length = str.length;
|
|
1051
1544
|
let i = 0;
|
|
@@ -1054,7 +1547,7 @@ class StrUtil {
|
|
|
1054
1547
|
result = str;
|
|
1055
1548
|
}
|
|
1056
1549
|
else {
|
|
1057
|
-
while (i < length && str[i] === ' ') {
|
|
1550
|
+
while (i < length && str[i] === ' ' /*' '*/) {
|
|
1058
1551
|
i = i + 1;
|
|
1059
1552
|
}
|
|
1060
1553
|
if (i > 0) {
|
|
@@ -1064,6 +1557,16 @@ class StrUtil {
|
|
|
1064
1557
|
}
|
|
1065
1558
|
return result;
|
|
1066
1559
|
}
|
|
1560
|
+
/// <summary>This function for Deleting String from end & start of input
|
|
1561
|
+
/// String
|
|
1562
|
+
/// </summary>
|
|
1563
|
+
/// <param name="str">String , which can include strToDelete spaces on input
|
|
1564
|
+
/// </param>
|
|
1565
|
+
/// <param name="strToDelete">need delete this String from start/end of str.
|
|
1566
|
+
/// </param>
|
|
1567
|
+
/// <returns> String without strToDelete on end & start,
|
|
1568
|
+
/// or 'null' if Sting hasn't not characters inside
|
|
1569
|
+
/// </returns>
|
|
1067
1570
|
static DeleteStringsFromEnds(str, strToDelete) {
|
|
1068
1571
|
if (str.startsWith(strToDelete)) {
|
|
1069
1572
|
str = str.substr(strToDelete.length);
|
|
@@ -1080,6 +1583,11 @@ class StrUtil {
|
|
|
1080
1583
|
}
|
|
1081
1584
|
return result;
|
|
1082
1585
|
}
|
|
1586
|
+
/// <summary> pad a string with trailing spaces up to the given length</summary>
|
|
1587
|
+
/// <param name="str">the string to pad
|
|
1588
|
+
/// </param>
|
|
1589
|
+
/// <param name="len">the expected length after padding
|
|
1590
|
+
/// </param>
|
|
1083
1591
|
static padStr(str, len) {
|
|
1084
1592
|
let padLen = len - str.length;
|
|
1085
1593
|
if (padLen > 0) {
|
|
@@ -1093,9 +1601,67 @@ class StrUtil {
|
|
|
1093
1601
|
}
|
|
1094
1602
|
return str;
|
|
1095
1603
|
}
|
|
1604
|
+
/// <summary> this method will serve as a string tokenizer instead of using the c# split method
|
|
1605
|
+
/// since there are diffrences btween java tokenizer and c# split
|
|
1606
|
+
/// the implimentation given by the conversion tool is not Sufficient
|
|
1607
|
+
/// </summary>
|
|
1608
|
+
/// <param name="source">- the source string to be converted
|
|
1609
|
+
/// </param>
|
|
1610
|
+
/// <param name="delim">- the string of delimiters used to split the string (each character in the String is a delimiter
|
|
1611
|
+
/// </param>
|
|
1612
|
+
/// <returns> array of token according which is the same as string tokenizer in java
|
|
1613
|
+
/// </returns>
|
|
1096
1614
|
static tokenize(source, delim) {
|
|
1615
|
+
// It is mentioned in the comment that we should not use String.Split()
|
|
1616
|
+
// because its behavior is different than Java's tokenizer.
|
|
1617
|
+
// So, we were suppose to use our own implementation (the commented code below).
|
|
1618
|
+
// But all these years, we were calling XmlParser.getToken() which was actually
|
|
1619
|
+
// using String.Split(). And we didn't face any problem.
|
|
1620
|
+
// So, it seems that we do not have problem in using String.Split().
|
|
1621
|
+
// But now, we can improve the performance here...
|
|
1622
|
+
// XmlParser.getTokens() was getting a String[] using String.Split().
|
|
1623
|
+
// It was then creating a List<String> from this String[] and was returning it to
|
|
1624
|
+
// tokenize().
|
|
1625
|
+
// tokenize() was again converting this List<String> back to String[].
|
|
1626
|
+
// So why not call String.Split() directly?
|
|
1097
1627
|
return source.split(delim);
|
|
1098
|
-
|
|
1628
|
+
/*
|
|
1629
|
+
String [] tokens = null;
|
|
1630
|
+
|
|
1631
|
+
char [] delimArry = delim.toCharArray();
|
|
1632
|
+
|
|
1633
|
+
//since java discards delimiters from the start and end of the string and c# does not
|
|
1634
|
+
//we need to remove them manually
|
|
1635
|
+
// source = source.TrimEnd(delimArry);
|
|
1636
|
+
// source = source.TrimStart(delimArry);
|
|
1637
|
+
source = source.trim();
|
|
1638
|
+
|
|
1639
|
+
//now that we have remove starting and ending delimiters we can split
|
|
1640
|
+
tokens = source.Split(delimArry);
|
|
1641
|
+
|
|
1642
|
+
/*
|
|
1643
|
+
* only one problem: if we have two Subsequent delimiters for example :
|
|
1644
|
+
* the delimiter is ';' and the string is: "first;;second;third"
|
|
1645
|
+
* then in java String tokenizer will give us only 3 tokens :first,second and third
|
|
1646
|
+
* while is c# split wethod will return 4 tokens: first,empty string,second and third
|
|
1647
|
+
* we need to deal with that
|
|
1648
|
+
*/
|
|
1649
|
+
/*
|
|
1650
|
+
List res = new List();
|
|
1651
|
+
for (int i = 0 ; i < tokens.length; i++)
|
|
1652
|
+
{
|
|
1653
|
+
if (tokens[i] != "" )
|
|
1654
|
+
res.addItem(tokens[i]);
|
|
1655
|
+
}
|
|
1656
|
+
|
|
1657
|
+
return (String [])(res.getAllItems (String.class));*/
|
|
1658
|
+
}
|
|
1659
|
+
/// <summary>
|
|
1660
|
+
/// translate from string to hexa dump char by char
|
|
1661
|
+
/// </summary>
|
|
1662
|
+
/// <param name = "string">to translate it to the byte stream</param>
|
|
1663
|
+
/// <param name = "minLength">the minimal length of hexa digits for each char</param>
|
|
1664
|
+
/// <returns> the byte stream in form of string</returns>
|
|
1099
1665
|
static stringToHexaDump(str, minLength) {
|
|
1100
1666
|
let stringBuilder = new StringBuilder(str.length * minLength);
|
|
1101
1667
|
for (let indx = 0; indx < str.length; indx = indx + 1) {
|
|
@@ -1114,6 +1680,11 @@ class StrUtil {
|
|
|
1114
1680
|
}
|
|
1115
1681
|
return StrUtil.searchAndReplace_1(str, from, to);
|
|
1116
1682
|
}
|
|
1683
|
+
/// <summary> replace every appearance of 'from' in 'str' with 'to'</summary>
|
|
1684
|
+
/// <param name="str">the working base source string </param>
|
|
1685
|
+
/// <param name="from">the string to replace </param>
|
|
1686
|
+
/// <param name="to">the string use instead 'from' </param>
|
|
1687
|
+
/// <returns> modified String </returns>
|
|
1117
1688
|
static searchAndReplace_0(str, from, to) {
|
|
1118
1689
|
let lastSubStr = 0;
|
|
1119
1690
|
let startSubStr;
|
|
@@ -1134,6 +1705,11 @@ class StrUtil {
|
|
|
1134
1705
|
}
|
|
1135
1706
|
return result;
|
|
1136
1707
|
}
|
|
1708
|
+
/// <summary> replace every appearance of strings of 'from' in 'str' with the according string in 'to'</summary>
|
|
1709
|
+
/// <param name="str">the working base source string </param>
|
|
1710
|
+
/// <param name="from">the string to replace </param>
|
|
1711
|
+
/// <param name="to">the string use instead 'from' </param>
|
|
1712
|
+
/// <returns> modified String </returns>
|
|
1137
1713
|
static searchAndReplace_1(str, from, to) {
|
|
1138
1714
|
let lastSubStr = 0;
|
|
1139
1715
|
let sarIndex = 0;
|
|
@@ -1158,6 +1734,14 @@ class StrUtil {
|
|
|
1158
1734
|
result = tmpBuf.ToString();
|
|
1159
1735
|
return result;
|
|
1160
1736
|
}
|
|
1737
|
+
/// <summary> this functions is for use by the searchAndReplace() function -
|
|
1738
|
+
/// searches the offset of the strings from the array in the given string
|
|
1739
|
+
/// and returns the minimum offset found and sets the index of the found string
|
|
1740
|
+
/// to SARindex
|
|
1741
|
+
/// </summary>
|
|
1742
|
+
/// <param name="str">the string to search in </param>
|
|
1743
|
+
/// <param name="strings">an array of strings to search for </param>
|
|
1744
|
+
/// <param name="offset">where to start the search </param>
|
|
1161
1745
|
static indexOf(str, strings, offset, SARindex) {
|
|
1162
1746
|
let minOffset = -1;
|
|
1163
1747
|
for (let i = 0; i < strings.length; i = i + 1) {
|
|
@@ -1184,6 +1768,15 @@ class StrUtil {
|
|
|
1184
1768
|
}
|
|
1185
1769
|
return result;
|
|
1186
1770
|
}
|
|
1771
|
+
/// <summary> replace tokens in user string by vector values </summary>
|
|
1772
|
+
/// <param name="userString">- user buffer like "User %d, %d string"
|
|
1773
|
+
/// </param>
|
|
1774
|
+
/// <param name="token">- token used in user string - i.e. "%d"
|
|
1775
|
+
/// </param>
|
|
1776
|
+
/// <param name="occurrence">- number of token where replace will take part (1 for first occurrence)
|
|
1777
|
+
/// </param>
|
|
1778
|
+
/// <param name="value">- value to be inserted insted of token
|
|
1779
|
+
/// </param>
|
|
1187
1780
|
static replaceStringTokens(userString, token, occurrence, val) {
|
|
1188
1781
|
let tokenLen = token.length;
|
|
1189
1782
|
let currPosition = 0;
|
|
@@ -1206,6 +1799,12 @@ class StrUtil {
|
|
|
1206
1799
|
}
|
|
1207
1800
|
StrUtil.makePrintableTokens_1(source, type);
|
|
1208
1801
|
}
|
|
1802
|
+
/// <summary>
|
|
1803
|
+
/// converts special characters in a token to a printable format
|
|
1804
|
+
/// </summary>
|
|
1805
|
+
/// <param name = "source">a token </param>
|
|
1806
|
+
/// <param name = "type">type of conversion: STR_2_HTML, SEQ_2_HTML, HTML_2_SEQ, HTML_2_STR, SEQ_2_STR </param>
|
|
1807
|
+
/// <returns> token with converted special characters </returns>
|
|
1209
1808
|
static makePrintableTokens_0(source, type) {
|
|
1210
1809
|
let escStr = [
|
|
1211
1810
|
"\\", "-", ","
|
|
@@ -1239,6 +1838,11 @@ class StrUtil {
|
|
|
1239
1838
|
}
|
|
1240
1839
|
return result;
|
|
1241
1840
|
}
|
|
1841
|
+
/// <summary>
|
|
1842
|
+
/// converts special characters in a tokens collection to a printable format
|
|
1843
|
+
/// </summary>
|
|
1844
|
+
/// <param name = "source">vector of strings before tokenaizer </param>
|
|
1845
|
+
/// <param name = "type">type of conversion: STR_2_HTML, SEQ_2_HTML, HTML_2_SEQ, HTML_2_STR </param>
|
|
1242
1846
|
static makePrintableTokens_1(source, type) {
|
|
1243
1847
|
if (source !== null) {
|
|
1244
1848
|
let length = source.length;
|
|
@@ -1248,6 +1852,12 @@ class StrUtil {
|
|
|
1248
1852
|
}
|
|
1249
1853
|
}
|
|
1250
1854
|
}
|
|
1855
|
+
/// <summary>
|
|
1856
|
+
/// change non-printable characters like "new line" and "line feed" to their
|
|
1857
|
+
/// printable representation
|
|
1858
|
+
/// </summary>
|
|
1859
|
+
/// <param name = "source">is the string with non-printable characters </param>
|
|
1860
|
+
/// <returns> the new string where all the non-printable characters are converted </returns>
|
|
1251
1861
|
static makePrintable(source) {
|
|
1252
1862
|
let from = [
|
|
1253
1863
|
"\n", "\r", "'", "\\", "\"", "\0"
|
|
@@ -1257,6 +1867,12 @@ class StrUtil {
|
|
|
1257
1867
|
];
|
|
1258
1868
|
return StrUtil.searchAndReplace(source, from, to);
|
|
1259
1869
|
}
|
|
1870
|
+
/// <summary>
|
|
1871
|
+
/// change non-printable characters like "new line" and "line feed" to their
|
|
1872
|
+
/// printable representation (simplified version for range error message)
|
|
1873
|
+
/// </summary>
|
|
1874
|
+
/// <param name = "source">is the string with non-printable characters </param>
|
|
1875
|
+
/// <returns> the new string where all the non-printable characters are converted </returns>
|
|
1260
1876
|
static makePrintable2(source) {
|
|
1261
1877
|
let from = [
|
|
1262
1878
|
"\n", "\r", "\0"
|
|
@@ -1266,10 +1882,21 @@ class StrUtil {
|
|
|
1266
1882
|
];
|
|
1267
1883
|
return StrUtil.searchAndReplace(source, from, to);
|
|
1268
1884
|
}
|
|
1885
|
+
/// <summary>
|
|
1886
|
+
///
|
|
1887
|
+
/// </summary>
|
|
1888
|
+
/// <param name="s"></param>
|
|
1889
|
+
/// <param name="len"></param>
|
|
1890
|
+
/// <returns></returns>
|
|
1269
1891
|
static ZstringMake(s, len) {
|
|
1270
1892
|
len = StrUtil.mem_trim(s, len);
|
|
1271
1893
|
return s.substr(0, len);
|
|
1272
1894
|
}
|
|
1895
|
+
/// <summary>(public)
|
|
1896
|
+
/// returns plain text from rtf text
|
|
1897
|
+
/// </summary>
|
|
1898
|
+
/// <param name="rtfText">refer to the summary</param>
|
|
1899
|
+
/// <returns>refer to the summary</returns>
|
|
1273
1900
|
static GetPlainTextfromRtf(rtfText) {
|
|
1274
1901
|
if (Rtf.isRtf(rtfText)) {
|
|
1275
1902
|
let rtf = new Rtf();
|
|
@@ -1279,6 +1906,12 @@ class StrUtil {
|
|
|
1279
1906
|
}
|
|
1280
1907
|
return rtfText;
|
|
1281
1908
|
}
|
|
1909
|
+
/// <summary>
|
|
1910
|
+
/// Returns true if the string arrays str1 & str2 are equal
|
|
1911
|
+
/// </summary>
|
|
1912
|
+
/// <param name="str1"></param>
|
|
1913
|
+
/// <param name="str2"></param>
|
|
1914
|
+
/// <returns></returns>
|
|
1282
1915
|
static StringsArraysEqual(str1, str2) {
|
|
1283
1916
|
let result;
|
|
1284
1917
|
if (str1 === null && str2 === null) {
|
|
@@ -1305,6 +1938,12 @@ class StrUtil {
|
|
|
1305
1938
|
}
|
|
1306
1939
|
return result;
|
|
1307
1940
|
}
|
|
1941
|
+
/// <summary>
|
|
1942
|
+
/// The code is copied from tsk_open_bnd_wild and SearchAndReplaceWildChars
|
|
1943
|
+
/// The refactoring is not performed for backwards compatibility
|
|
1944
|
+
/// The code replaces special charachters :* ? with recieved filler
|
|
1945
|
+
/// </summary>
|
|
1946
|
+
/// <returns></returns>
|
|
1308
1947
|
static SearchAndReplaceWildChars(buf, len, filler) {
|
|
1309
1948
|
buf = NString.PadRight(buf, len);
|
|
1310
1949
|
let escChar = false;
|
|
@@ -1314,6 +1953,7 @@ class StrUtil {
|
|
|
1314
1953
|
case ('\\'):
|
|
1315
1954
|
{
|
|
1316
1955
|
let isNextCharWild = true;
|
|
1956
|
+
//If next char is not wild , then copy '\', if this is first char.
|
|
1317
1957
|
if ((i + 1 < len) && (buf[i + 1] != '*' && buf[i + 1] != '\\'))
|
|
1318
1958
|
isNextCharWild = false;
|
|
1319
1959
|
if (escChar || !isNextCharWild)
|
|
@@ -1342,12 +1982,22 @@ class StrUtil {
|
|
|
1342
1982
|
let text = tmpBuf.ToString();
|
|
1343
1983
|
return NString.TrimEnd(NString.TrimEnd(text, ['\0']));
|
|
1344
1984
|
}
|
|
1985
|
+
/// <summary>
|
|
1986
|
+
/// Remove the task path delimiter from the error string.
|
|
1987
|
+
/// </summary>
|
|
1988
|
+
/// <param name = "source">string with delimiter </param>
|
|
1989
|
+
/// <returns> string for console error </returns>
|
|
1345
1990
|
static getConsoleErorString(source) {
|
|
1346
1991
|
let consoleErorString = "";
|
|
1347
1992
|
if (!isNullOrUndefined(source))
|
|
1348
1993
|
consoleErorString = this.searchAndReplace(source, TASK_PATH_DELIMITER, "");
|
|
1349
1994
|
return consoleErorString;
|
|
1350
1995
|
}
|
|
1996
|
+
/// <summary>
|
|
1997
|
+
/// Remove the task path from the error string.
|
|
1998
|
+
/// </summary>
|
|
1999
|
+
/// <param name = "source">string with delimiter </param>
|
|
2000
|
+
/// <returns> string for console error </returns>
|
|
1351
2001
|
static getMsgBoxErorString(source) {
|
|
1352
2002
|
let tokens;
|
|
1353
2003
|
let msgBoxErorString = new StringBuilder("");
|
|
@@ -1362,11 +2012,32 @@ class StrUtil {
|
|
|
1362
2012
|
}
|
|
1363
2013
|
}
|
|
1364
2014
|
|
|
2015
|
+
// In order to convert some functionality to Visual C#, the Java Language Conversion Assistant
|
|
2016
|
+
// creates "support classes" that duplicate the original functionality.
|
|
2017
|
+
//
|
|
2018
|
+
// Support classes replicate the functionality of the original code, but in some cases they are
|
|
2019
|
+
// substantially different architecturally. Although every effort is made to preserve the
|
|
2020
|
+
// original architecture of the application in the converted project, the user should be aware that
|
|
2021
|
+
// the primary goal of these support classes is to replicate functionality, and that at times
|
|
2022
|
+
// the architecture of the resulting solution may differ somewhat.
|
|
2023
|
+
/// <summary>
|
|
2024
|
+
/// Contains conversion support elements such as classes, interfaces and static methods.
|
|
2025
|
+
/// </summary>
|
|
1365
2026
|
class Misc {
|
|
2027
|
+
/// <summary>
|
|
2028
|
+
/// Writes the exception stack trace to the received stream
|
|
2029
|
+
/// </summary>
|
|
2030
|
+
/// <param name="throwable">Exception to obtain information from</param>
|
|
2031
|
+
/// <param name="stream">Output sream used to write to</param>
|
|
1366
2032
|
static WriteStackTrace(throwable) {
|
|
1367
2033
|
console.log(throwable.Message);
|
|
1368
2034
|
console.log(throwable.StackTrace);
|
|
1369
2035
|
}
|
|
2036
|
+
/// <summary>
|
|
2037
|
+
/// Receives a byte array and returns it transformed in an byte array
|
|
2038
|
+
/// </summary>
|
|
2039
|
+
/// <param name="byteArray">Byte array to process</param>
|
|
2040
|
+
/// <returns>The transformed array</returns>
|
|
1370
2041
|
static ToSByteArray(byteArray) {
|
|
1371
2042
|
let sbyteArray = null;
|
|
1372
2043
|
if (byteArray !== null) {
|
|
@@ -1377,6 +2048,11 @@ class Misc {
|
|
|
1377
2048
|
}
|
|
1378
2049
|
return sbyteArray;
|
|
1379
2050
|
}
|
|
2051
|
+
/// <summary>
|
|
2052
|
+
/// Receives sbyte array and returns it transformed in a byte array
|
|
2053
|
+
/// </summary>
|
|
2054
|
+
/// <param name="sbyteArray">sbyte array to process</param>
|
|
2055
|
+
/// <returns>The transformed array</returns>
|
|
1380
2056
|
static ToByteArray(sbyteArray) {
|
|
1381
2057
|
let byteArray = null;
|
|
1382
2058
|
if (sbyteArray !== null) {
|
|
@@ -1387,6 +2063,11 @@ class Misc {
|
|
|
1387
2063
|
}
|
|
1388
2064
|
return byteArray;
|
|
1389
2065
|
}
|
|
2066
|
+
/// <summary> Compares number of bytes in two byte arrays</summary>
|
|
2067
|
+
/// <param name="source"></param>
|
|
2068
|
+
/// <param name="destination"></param>
|
|
2069
|
+
/// <param name="numberOfBytes"></param>
|
|
2070
|
+
/// <returns> boolen true if equal</returns>
|
|
1390
2071
|
static CompareByteArray(source, destination, numberOfBytes) {
|
|
1391
2072
|
if (source.length >= numberOfBytes && destination.length >= numberOfBytes) {
|
|
1392
2073
|
for (let len = 0; len < numberOfBytes; len++) {
|
|
@@ -1398,6 +2079,13 @@ class Misc {
|
|
|
1398
2079
|
return false;
|
|
1399
2080
|
return true;
|
|
1400
2081
|
}
|
|
2082
|
+
/// <summary>
|
|
2083
|
+
/// Performs an unsigned bitwise right shift with the specified number
|
|
2084
|
+
/// </summary>
|
|
2085
|
+
/// <param name="number">Number to operate on</param>
|
|
2086
|
+
/// <param name="bits">Ammount of bits to shift</param>
|
|
2087
|
+
/// <returns>The resulting number from the shift operation</returns>
|
|
2088
|
+
// TODO: instead of calling URShift(number, bits), we can use((uint)number) >> bits.
|
|
1401
2089
|
static URShift(number, bits) {
|
|
1402
2090
|
let result;
|
|
1403
2091
|
if (number >= 0) {
|
|
@@ -1408,9 +2096,20 @@ class Misc {
|
|
|
1408
2096
|
}
|
|
1409
2097
|
return result;
|
|
1410
2098
|
}
|
|
2099
|
+
/// <summary>
|
|
2100
|
+
/// get system's time in milliseconds
|
|
2101
|
+
/// </summary>
|
|
2102
|
+
/// <returns></returns>
|
|
1411
2103
|
static getSystemMilliseconds() {
|
|
2104
|
+
// TODO - check if we need this adjustment
|
|
1412
2105
|
return Math.floor((DateTime.Now.Ticks - 621355968000000000) / 10000);
|
|
1413
2106
|
}
|
|
2107
|
+
/// <summary>
|
|
2108
|
+
/// Compares 2 int arrays
|
|
2109
|
+
/// </summary>
|
|
2110
|
+
/// <param name="arrayOne"></param>
|
|
2111
|
+
/// <param name="arrayTwo"></param>
|
|
2112
|
+
/// <returns>true if arrays are equal else false</returns>
|
|
1414
2113
|
static CompareIntArrays(arrayOne, arrayTwo) {
|
|
1415
2114
|
let areEqual = false;
|
|
1416
2115
|
if (arrayOne === arrayTwo) {
|
|
@@ -1430,6 +2129,11 @@ class Misc {
|
|
|
1430
2129
|
}
|
|
1431
2130
|
return areEqual;
|
|
1432
2131
|
}
|
|
2132
|
+
/// <summary>
|
|
2133
|
+
/// Returns the comma separated string for the values passed in int array.
|
|
2134
|
+
/// </summary>
|
|
2135
|
+
/// <param name="values">Integer array</param>
|
|
2136
|
+
/// <returns>comma separated string</returns>
|
|
1433
2137
|
static GetCommaSeperatedString(intArray) {
|
|
1434
2138
|
let temp = new StringBuilder();
|
|
1435
2139
|
for (let val = 0; val < intArray.length; val = val + 1) {
|
|
@@ -1441,6 +2145,11 @@ class Misc {
|
|
|
1441
2145
|
}
|
|
1442
2146
|
return temp.ToString();
|
|
1443
2147
|
}
|
|
2148
|
+
/// <summary>
|
|
2149
|
+
/// Returns int array out of comma separated string
|
|
2150
|
+
/// </summary>
|
|
2151
|
+
/// <param name="value">comma separated string</param>
|
|
2152
|
+
/// <returns>Integer array</returns>
|
|
1444
2153
|
static GetIntArray(commaSeparatedValue) {
|
|
1445
2154
|
let intArray = new Array(0);
|
|
1446
2155
|
if (!NString.IsNullOrEmpty(commaSeparatedValue)) {
|
|
@@ -1468,6 +2177,14 @@ class Base64 {
|
|
|
1468
2177
|
else
|
|
1469
2178
|
return Base64.encode_1(str, isUseEnvCharset, encoding);
|
|
1470
2179
|
}
|
|
2180
|
+
/// <summary> Encodes string using the base64-encoding.
|
|
2181
|
+
/// If isUseEnvCharset is true, use the specific charset when converting
|
|
2182
|
+
/// string to byte array. (DBCS support)
|
|
2183
|
+
/// </summary>
|
|
2184
|
+
/// <param name="str">the string </param>
|
|
2185
|
+
/// <param name="isUseEnvCharset"> </param>
|
|
2186
|
+
/// <param name="encoding"> Environment.Encoding </param>
|
|
2187
|
+
/// <returns> the base64-encoded str </returns>
|
|
1471
2188
|
static encode_1(str, isUseEnvCharset, encoding) {
|
|
1472
2189
|
let result;
|
|
1473
2190
|
if (str === null) {
|
|
@@ -1496,12 +2213,18 @@ class Base64 {
|
|
|
1496
2213
|
}
|
|
1497
2214
|
return result;
|
|
1498
2215
|
}
|
|
2216
|
+
/// <summary> This method encodes the given byte[] using the base64-encoding
|
|
2217
|
+
/// specified in RFC-2045 (Section 6.8).
|
|
2218
|
+
/// </summary>
|
|
2219
|
+
/// <param name="data">the data </param>
|
|
2220
|
+
/// <returns> the base64-encoded data </returns>
|
|
1499
2221
|
static encodeBytes(data) {
|
|
1500
2222
|
if (data === null)
|
|
1501
2223
|
return null;
|
|
1502
2224
|
let dest = new Uint8Array(Math.floor((data.length + 2) / 3) * 4);
|
|
1503
2225
|
let sidx = 0;
|
|
1504
2226
|
let didx = 0;
|
|
2227
|
+
// 3-byte to 4-byte conversion + 0-63 to ASCII printable conversion
|
|
1505
2228
|
while (sidx < data.length - 2) {
|
|
1506
2229
|
dest[didx++] = Base64._base64EncMap[Misc.URShift(data[sidx], 2) & 63];
|
|
1507
2230
|
dest[didx++] = Base64._base64EncMap[(Misc.URShift(data[sidx + 1], 4) & 15) | (data[sidx] << 4 & 63)];
|
|
@@ -1519,6 +2242,7 @@ class Base64 {
|
|
|
1519
2242
|
dest[didx++] = Base64._base64EncMap[data[sidx] << 4 & 63];
|
|
1520
2243
|
}
|
|
1521
2244
|
}
|
|
2245
|
+
// add padding
|
|
1522
2246
|
while (didx < dest.length) {
|
|
1523
2247
|
dest[didx] = 61;
|
|
1524
2248
|
didx = didx + 1;
|
|
@@ -1530,6 +2254,12 @@ class Base64 {
|
|
|
1530
2254
|
encoding = null;
|
|
1531
2255
|
return Base64.decode_1(str, encoding);
|
|
1532
2256
|
}
|
|
2257
|
+
/// <summary> This method decodes the given string using the base64-encoding
|
|
2258
|
+
/// specified in RFC-2045 (Section 6.8).
|
|
2259
|
+
/// </summary>
|
|
2260
|
+
/// <param name="str">the base64-encoded string. </param>
|
|
2261
|
+
/// <param name="encoding">Environment.Encoding or null.</param>
|
|
2262
|
+
/// <returns> the decoded str.</returns>
|
|
1533
2263
|
static decode_1(str, encoding) {
|
|
1534
2264
|
let result;
|
|
1535
2265
|
if (str === null) {
|
|
@@ -1558,6 +2288,11 @@ class Base64 {
|
|
|
1558
2288
|
}
|
|
1559
2289
|
return result;
|
|
1560
2290
|
}
|
|
2291
|
+
/// <summary> This method decodes the given byte[] using the base64-encoding
|
|
2292
|
+
/// specified in RFC-2045 (Section 6.8).
|
|
2293
|
+
/// </summary>
|
|
2294
|
+
/// <param name="data">the base64-encoded data.</param>
|
|
2295
|
+
/// <returns> the decoded <var>data</va
|
|
1561
2296
|
static decodeBytes(data) {
|
|
1562
2297
|
if (data === null)
|
|
1563
2298
|
return null;
|
|
@@ -1566,9 +2301,11 @@ class Base64 {
|
|
|
1566
2301
|
tail = tail - 1;
|
|
1567
2302
|
}
|
|
1568
2303
|
let dest = new Uint8Array(tail - Math.floor(data.length / 4));
|
|
2304
|
+
// ASCII printable to 0-63 conversion
|
|
1569
2305
|
for (let idx = 0; idx < data.length; idx = idx + 1) {
|
|
1570
2306
|
data[idx] = Base64._base64DecMap[data[idx]];
|
|
1571
2307
|
}
|
|
2308
|
+
// 4-byte to 3-byte conversion
|
|
1572
2309
|
let sidx = 0;
|
|
1573
2310
|
let didx;
|
|
1574
2311
|
for (didx = 0; didx < dest.length - 2; didx = didx + 3) {
|
|
@@ -1583,6 +2320,7 @@ class Base64 {
|
|
|
1583
2320
|
dest[didx] = (((data[sidx + 1] << 4) & 255) | (Misc.URShift(data[sidx + 2], 2) & 15));
|
|
1584
2321
|
return dest;
|
|
1585
2322
|
}
|
|
2323
|
+
/// <summary> decoded and return an hex representation of the data</summary>
|
|
1586
2324
|
static decodeToHex(str) {
|
|
1587
2325
|
if (str === null)
|
|
1588
2326
|
return null;
|
|
@@ -1590,9 +2328,13 @@ class Base64 {
|
|
|
1590
2328
|
return str;
|
|
1591
2329
|
return StrUtil.stringToHexaDump(Base64.decode(str), 2);
|
|
1592
2330
|
}
|
|
2331
|
+
/// <summary> decodes a string to byte array</summary>
|
|
1593
2332
|
static decodeToByte(str) {
|
|
1594
2333
|
if (str === null)
|
|
1595
2334
|
return null;
|
|
2335
|
+
// QCR 740918 if we have and empty expression it is sent from the server as empty string
|
|
2336
|
+
// and changed locally to a string with one blank either way they are not valid base64 encoded
|
|
2337
|
+
// string and should not be decoded.
|
|
1596
2338
|
if (str === "" || str === " ")
|
|
1597
2339
|
return new Uint8Array(0);
|
|
1598
2340
|
try {
|
|
@@ -1621,6 +2363,18 @@ class Base64 {
|
|
|
1621
2363
|
}
|
|
1622
2364
|
|
|
1623
2365
|
class ChoiceUtils {
|
|
2366
|
+
/// <summary>
|
|
2367
|
+
/// init the display Value from string
|
|
2368
|
+
/// </summary>
|
|
2369
|
+
/// <param name = "choiceDispStr">the all substring separated with comma.
|
|
2370
|
+
/// The behavior:
|
|
2371
|
+
/// a. when have "\" before char a-z need to ignore the \ put the a-z char
|
|
2372
|
+
/// b. when "\," -> ","
|
|
2373
|
+
/// c. when "\-" -> "-"
|
|
2374
|
+
/// d. when "\\" -> "\"
|
|
2375
|
+
/// e. when "\\\\" -> "\\"
|
|
2376
|
+
/// the display can be all string. and we don't need to check validation according to the dataType(as we do in Link
|
|
2377
|
+
/// </param>
|
|
1624
2378
|
static GetDisplayListFromString(choiceDispStr, removeAccelerators, shouldMakePrintable, shouldTrimOptions) {
|
|
1625
2379
|
let fromHelp = new Array("\\\\", "\\-", "\\,");
|
|
1626
2380
|
let toHelp = new Array("XX", "XX", "XX");
|
|
@@ -1697,12 +2451,16 @@ class ChoiceUtils {
|
|
|
1697
2451
|
}
|
|
1698
2452
|
}
|
|
1699
2453
|
|
|
2454
|
+
//This class contains all the constants which are used in MgxpaRIA.exe as well as in MgGui.dll.
|
|
1700
2455
|
class Constants {
|
|
2456
|
+
/// <summary> Null Arithmetic values</summary>
|
|
1701
2457
|
static NULL_ARITH_NULLIFY = 'N';
|
|
1702
2458
|
static NULL_ARITH_USE_DEF = 'U';
|
|
2459
|
+
/// <summary> select program : select mode property</summary>
|
|
1703
2460
|
static SELPRG_MODE_BEFORE = 'B';
|
|
1704
2461
|
static SELPRG_MODE_AFTER = 'A';
|
|
1705
2462
|
static SELPRG_MODE_PROMPT = 'P';
|
|
2463
|
+
/// <summary> move in View</summary>
|
|
1706
2464
|
static MOVE_UNIT_TABLE = 'T';
|
|
1707
2465
|
static MOVE_UNIT_PAGE = 'P';
|
|
1708
2466
|
static MOVE_UNIT_ROW = 'R';
|
|
@@ -1716,6 +2474,7 @@ class Constants {
|
|
|
1716
2474
|
static MOVE_DIRECTION_FIRST_SON = 'F';
|
|
1717
2475
|
static MOVE_DIRECTION_NEXT_SIBLING = 'X';
|
|
1718
2476
|
static MOVE_DIRECTION_PREV_SIBLING = 'V';
|
|
2477
|
+
/// <summary> refresh types for a task form</summary>
|
|
1719
2478
|
static TASK_REFRESH_FORM = 'F';
|
|
1720
2479
|
static TASK_REFRESH_TABLE = 'T';
|
|
1721
2480
|
static TASK_REFRESH_TREE_AND_FORM = 'R';
|
|
@@ -1726,12 +2485,15 @@ class Constants {
|
|
|
1726
2485
|
static TASK_MODE_CREATE = 'C';
|
|
1727
2486
|
static TASK_MODE_DELETE = 'D';
|
|
1728
2487
|
static TASK_MODE_NONE = ' ';
|
|
2488
|
+
/// <summary> task level</summary>
|
|
1729
2489
|
static TASK_LEVEL_NONE = ' ';
|
|
1730
2490
|
static TASK_LEVEL_TASK = 'T';
|
|
1731
2491
|
static TASK_LEVEL_RECORD = 'R';
|
|
1732
2492
|
static TASK_LEVEL_CONTROL = 'C';
|
|
2493
|
+
/// <summary> special records constants</summary>
|
|
1733
2494
|
static MG_DATAVIEW_FIRST_RECORD = Int32.MinValue;
|
|
1734
2495
|
static MG_DATAVIEW_LAST_RECORD = Int32.MaxValue;
|
|
2496
|
+
/// <summary> action states for keyboard mapping</summary>
|
|
1735
2497
|
static ACT_STT_TBL_SCREEN_MODE = 0x0001;
|
|
1736
2498
|
static ACT_STT_TBL_LEFT_TO_RIGHT = 0x0002;
|
|
1737
2499
|
static ACT_STT_TBL_SCREEN_TOP = 0x0004;
|
|
@@ -1746,13 +2508,17 @@ class Constants {
|
|
|
1746
2508
|
static ACT_STT_EDT_EDITING = 0x0800;
|
|
1747
2509
|
static ACT_STT_TREE_PARK = 0x1000;
|
|
1748
2510
|
static ACT_STT_TREE_EDITING = 0x2000;
|
|
1749
|
-
static ForwardSlashWebUsage = "web";
|
|
2511
|
+
static ForwardSlashWebUsage = "web"; // refer to a forward slash as a relative web url.
|
|
1750
2512
|
static HTTP_PROTOCOL = "http://";
|
|
1751
2513
|
static HTTPS_PROTOCOL = "https://";
|
|
1752
2514
|
static FILE_PROTOCOL = "file://";
|
|
2515
|
+
/// <summary>threads constants</summary>
|
|
1753
2516
|
static MG_GUI_THREAD = "MG_GUI_THREAD";
|
|
1754
2517
|
static MG_WORK_THREAD = "MG_WORK_THREAD";
|
|
1755
2518
|
static MG_TIMER_THREAD = "MG_TIMER_THREAD";
|
|
2519
|
+
/// <summary>
|
|
2520
|
+
/// property name for the runtime designer
|
|
2521
|
+
/// </summary>
|
|
1756
2522
|
static ConfigurationFilePropertyName = "Configuration file";
|
|
1757
2523
|
static WinPropText = "Text";
|
|
1758
2524
|
static WinPropLayer = "Layer";
|
|
@@ -1786,9 +2552,12 @@ class XMLConstants {
|
|
|
1786
2552
|
static MG_TAG_TASK = "task";
|
|
1787
2553
|
static MG_TAG_TASK_END = "/task";
|
|
1788
2554
|
static MG_TAG_RECOMPUTE = "recompute";
|
|
2555
|
+
//TODO: this class contains the constants which are used for XML parsing.
|
|
2556
|
+
//Check if we can move it to Util.dll
|
|
1789
2557
|
static MG_ATTR_VB_VIEW_ROWIDX = "db_view_rowidx";
|
|
1790
2558
|
static MG_ATTR_CONTROL_ISN = "controlIsn";
|
|
1791
2559
|
static MG_HOR_ALIGMENT_IS_INHERITED = "horizontalAlignmentIsFromSystemDefault";
|
|
2560
|
+
// MainHeaders
|
|
1792
2561
|
static MAX_PATH = 260;
|
|
1793
2562
|
static FILE_NAME_SIZE = XMLConstants.MAX_PATH + 1;
|
|
1794
2563
|
static CDATA_START = "<![CDATA[";
|
|
@@ -1874,11 +2643,13 @@ class XMLConstants {
|
|
|
1874
2643
|
static MG_ATTR_IS_GUI_THREAD_EXECUTION = "isGuiThreadExecution";
|
|
1875
2644
|
static MG_TAG_TASKDEFINITIONID_ENTRY = "taskDefinitionId";
|
|
1876
2645
|
static MG_TAG_OBJECT_REFERENCE = "objectRef";
|
|
2646
|
+
//Help types
|
|
1877
2647
|
static MG_ATTR_HLP_TYP_TOOLTIP = "T";
|
|
1878
2648
|
static MG_ATTR_HLP_TYP_PROMPT = "P";
|
|
1879
2649
|
static MG_ATTR_HLP_TYP_URL = "U";
|
|
1880
2650
|
static MG_ATTR_HLP_TYP_INTERNAL = "I";
|
|
1881
2651
|
static MG_ATTR_HLP_TYP_WINDOWS = "W";
|
|
2652
|
+
//Internal help attributes.
|
|
1882
2653
|
static MG_ATTR_INTERNAL_HELP_TYPE = "type";
|
|
1883
2654
|
static MG_ATTR_INTERNAL_HELP_NAME = "name";
|
|
1884
2655
|
static MG_ATTR_INTERNAL_HELP_FRAMEX = "framex";
|
|
@@ -1893,20 +2664,26 @@ class XMLConstants {
|
|
|
1893
2664
|
static MG_ATTR_INTERNAL_TITLE_BAR = "titlebar";
|
|
1894
2665
|
static MG_ATTR_INTERNAL_HELP_SYSTEM_MENU = "sysmenu";
|
|
1895
2666
|
static MG_ATTR_INTERNAL_HELP_FONT_TABLE_INDEX = "fonttableindex";
|
|
2667
|
+
//Windows help attributes.
|
|
1896
2668
|
static MG_ATTR_WINDOWS_HELP_FILE = "file";
|
|
1897
2669
|
static MG_ATTR_WINDOWS_HELP_COMMAND = "command";
|
|
1898
2670
|
static MG_ATTR_WINDOWS_HELP_KEY = "key";
|
|
2671
|
+
//Print data attributes.
|
|
1899
2672
|
static MG_TAG_PRINT_DATA = "Print_data";
|
|
1900
2673
|
static MG_TAG_PRINT_DATA_END = "/Print_data";
|
|
1901
2674
|
static MG_TAG_RECORD = "Record";
|
|
1902
2675
|
static MG_TAG_RECORD_END = "/Record";
|
|
2676
|
+
//Custom Validators attributes.
|
|
1903
2677
|
static MG_TAG_CUSTOM_VALIDATORS = "CustomValidators";
|
|
1904
2678
|
static MG_TAG_CUSTOM_VALIDATORS_END = "/CustomValidators";
|
|
1905
2679
|
static MG_TAG_CUSTOM_VALIDATOR = "CustomValidator";
|
|
2680
|
+
// date/time formats for DateTimeUtils
|
|
2681
|
+
//TODO: isolate to a different file?
|
|
1906
2682
|
static ERROR_LOG_TIME_FORMAT = "HH:mm:ss.S";
|
|
1907
2683
|
static ERROR_LOG_DATE_FORMAT = "DD/MM/YYYY";
|
|
1908
2684
|
static HTTP_ERROR_TIME_FORMAT = "HH:mm:ss";
|
|
1909
2685
|
static CACHED_DATE_TIME_FORMAT = "DD/MM/YYYY HH:mm:ss";
|
|
2686
|
+
//webs constants
|
|
1910
2687
|
static MG_TAG_WS_READ_REQUEST = "Read";
|
|
1911
2688
|
static MG_TAG_WS_CREATE_REQUEST = "Create";
|
|
1912
2689
|
static MG_TAG_WS_CREATE_REQUEST_END = "/Create";
|
|
@@ -1940,6 +2717,7 @@ class XMLConstants {
|
|
|
1940
2717
|
}
|
|
1941
2718
|
|
|
1942
2719
|
class DateTimeUtils {
|
|
2720
|
+
/// <summary> returns the number in a 2 digit string
|
|
1943
2721
|
static int2str(n) {
|
|
1944
2722
|
return (n > 9) ? n.toString() : ("0" + n);
|
|
1945
2723
|
}
|
|
@@ -1991,7 +2769,13 @@ class DateTimeUtils {
|
|
|
1991
2769
|
}
|
|
1992
2770
|
}
|
|
1993
2771
|
|
|
2772
|
+
/// <summary>
|
|
2773
|
+
/// An interface to define the constantes used by the Picture mechanism.
|
|
2774
|
+
/// </summary>
|
|
1994
2775
|
class PICInterface {
|
|
2776
|
+
//--------------------------------------------------------------------------
|
|
2777
|
+
// TEMP!
|
|
2778
|
+
//--------------------------------------------------------------------------
|
|
1995
2779
|
static PIC_X = 1;
|
|
1996
2780
|
static PIC_U = 2;
|
|
1997
2781
|
static PIC_L = 3;
|
|
@@ -2009,30 +2793,32 @@ class PICInterface {
|
|
|
2009
2793
|
static PIC_MMT = 15;
|
|
2010
2794
|
static PIC_SS = 16;
|
|
2011
2795
|
static PIC_PM = 17;
|
|
2012
|
-
static PIC_HYYYYY = 18;
|
|
2013
|
-
static PIC_HL = 19;
|
|
2014
|
-
static PIC_HDD = 20;
|
|
2015
|
-
static PIC_MS = 21;
|
|
2016
|
-
static PIC_LOCAL = 23;
|
|
2796
|
+
static PIC_HYYYYY = 18; // Hebrew year
|
|
2797
|
+
static PIC_HL = 19; // Hebrew thousand year
|
|
2798
|
+
static PIC_HDD = 20; // Hebrew day of month
|
|
2799
|
+
static PIC_MS = 21; // Milliseconds
|
|
2800
|
+
static PIC_LOCAL = 23; // the space between PIC_LOCAL and PIC_MAX_OP
|
|
2017
2801
|
static PIC_MAX_MSK_LEN = 100;
|
|
2018
|
-
|
|
2019
|
-
static
|
|
2020
|
-
static
|
|
2021
|
-
static
|
|
2022
|
-
static
|
|
2023
|
-
static
|
|
2024
|
-
|
|
2025
|
-
static
|
|
2026
|
-
static
|
|
2027
|
-
static
|
|
2802
|
+
// JPN: Japanese date picture support
|
|
2803
|
+
static PIC_JY1 = PICInterface.PIC_LOCAL + 0; // the name of an era (1 byte)
|
|
2804
|
+
static PIC_JY2 = PICInterface.PIC_LOCAL + 1; // the name of an era (2 bytes)
|
|
2805
|
+
static PIC_JY4 = PICInterface.PIC_LOCAL + 2; // the name of an era (4 bytes)
|
|
2806
|
+
static PIC_YJ = PICInterface.PIC_LOCAL + 3; // a year of an era
|
|
2807
|
+
static PIC_BB = PICInterface.PIC_LOCAL + 4; // a day of the week (2, 4 or 6 bytes)
|
|
2808
|
+
// DBCS pictures for iSeries
|
|
2809
|
+
static PIC_J = PICInterface.PIC_LOCAL + 5; // DBCS only (with SO/SI)
|
|
2810
|
+
static PIC_T = PICInterface.PIC_LOCAL + 6; // All SBCS or All DBCS (with SO/SI)
|
|
2811
|
+
static PIC_G = PICInterface.PIC_LOCAL + 7; // DBCS only (without SO/SI)
|
|
2812
|
+
static PIC_S = PICInterface.PIC_LOCAL + 8; // SBCS only
|
|
2813
|
+
static PIC_MAX_OP = 31; // is reserved for DLL"s picture
|
|
2028
2814
|
static NULL_CHAR = -1;
|
|
2029
2815
|
static DB_STR_MAX = 255;
|
|
2030
|
-
static DAYSINFOURCENT = 146097;
|
|
2031
|
-
static DAYSINCENTURY = 36524;
|
|
2032
|
-
static DAYSINFOURYEAR = 1461;
|
|
2816
|
+
static DAYSINFOURCENT = 146097; // ((365*4+1)*25-1)*4+1 */
|
|
2817
|
+
static DAYSINCENTURY = 36524; // (365*4+1)*25-1 */
|
|
2818
|
+
static DAYSINFOURYEAR = 1461; // 365*4+1 */
|
|
2033
2819
|
static DAYSINYEAR = 365;
|
|
2034
2820
|
static DAYSINMONTH = 31;
|
|
2035
|
-
static DATE_BUDDHIST_GAP = 543;
|
|
2821
|
+
static DATE_BUDDHIST_GAP = 543; // years above the gregorian date
|
|
2036
2822
|
static DEFAULT_DATE = "693961";
|
|
2037
2823
|
static DEFAULT_TIME = "0";
|
|
2038
2824
|
static date_day_tab = [
|
|
@@ -2044,6 +2830,9 @@ class PICInterface {
|
|
|
2044
2830
|
static date_dow_str = [
|
|
2045
2831
|
" ", "Sunday ", "Monday ", "Tuesday ", "Wednesday ", "Thursday ", "Friday ", "Saturday "
|
|
2046
2832
|
];
|
|
2833
|
+
//public final static readonly int DEF_century = 1920;
|
|
2834
|
+
//public final static readonly Nchar DEF_date_mode = 'E';
|
|
2835
|
+
// vec of pictures that can be given a numeric char only
|
|
2047
2836
|
static NumDirective = [
|
|
2048
2837
|
4, 5, 6, 7, 9, 10, 11, 12, 14, 15, 16
|
|
2049
2838
|
];
|
|
@@ -2056,9 +2845,15 @@ const DATE_DOW_LEN = 10;
|
|
|
2056
2845
|
class DateUtil {
|
|
2057
2846
|
static _localMonths = new Array(13);
|
|
2058
2847
|
static _localDays = new Array(8);
|
|
2848
|
+
/// <summary>
|
|
2849
|
+
/// extract the vector which contains the names of the months, as specified by the
|
|
2850
|
+
/// language CAB
|
|
2851
|
+
/// </summary>
|
|
2059
2852
|
static getLocalMonths(names) {
|
|
2060
2853
|
let monthLen = DATE_MONTH_LEN;
|
|
2854
|
+
// if it's the first time then access the language CAB and take the values
|
|
2061
2855
|
if (typeof DateUtil._localMonths[0] === "undefined") {
|
|
2856
|
+
//cut the string into separate values
|
|
2062
2857
|
if (names !== null) {
|
|
2063
2858
|
DateUtil._localMonths[0] = PICInterface.date_month_str[0];
|
|
2064
2859
|
for (let i = 1; i < DateUtil._localMonths.length; i = i + 1) {
|
|
@@ -2081,9 +2876,15 @@ class DateUtil {
|
|
|
2081
2876
|
}
|
|
2082
2877
|
return DateUtil._localMonths;
|
|
2083
2878
|
}
|
|
2879
|
+
/// <summary>
|
|
2880
|
+
/// extract the vector which contains the names of the days, as specified by the
|
|
2881
|
+
/// language CAB
|
|
2882
|
+
/// </summary>
|
|
2084
2883
|
static getLocalDays(names) {
|
|
2085
2884
|
let dowLen = DATE_DOW_LEN;
|
|
2885
|
+
// if it's the first time then access the language CAB and take the values
|
|
2086
2886
|
if (typeof DateUtil._localDays[0] === "undefined") {
|
|
2887
|
+
//cut the string into separate values
|
|
2087
2888
|
if (names !== null) {
|
|
2088
2889
|
DateUtil._localDays[0] = PICInterface.date_dow_str[0];
|
|
2089
2890
|
for (let i = 1; i < DateUtil._localDays.length; i = i + 1) {
|
|
@@ -3871,6 +4672,7 @@ var NotifyCollectionChangedAction;
|
|
|
3871
4672
|
NotifyCollectionChangedAction[NotifyCollectionChangedAction["Reset"] = 4] = "Reset";
|
|
3872
4673
|
})(NotifyCollectionChangedAction || (NotifyCollectionChangedAction = {}));
|
|
3873
4674
|
|
|
4675
|
+
/// <summary> this interface defines the internal events codes</summary>
|
|
3874
4676
|
class InternalInterface {
|
|
3875
4677
|
static MG_ACT_NONE = 0;
|
|
3876
4678
|
static MG_ACT_CHAR = 1;
|
|
@@ -4174,6 +4976,7 @@ class InternalInterface {
|
|
|
4174
4976
|
static MG_ACT_CONTEXT_REMOVE = 647;
|
|
4175
4977
|
static MG_ACT_DUMP_ENVIRONMENT = 653;
|
|
4176
4978
|
static MG_ACT_TOT_CNT = 654;
|
|
4979
|
+
// NEW INTERNAL EVENTS
|
|
4177
4980
|
static MG_ACT_TASK_PREFIX = 1001;
|
|
4178
4981
|
static MG_ACT_TASK_SUFFIX = 1002;
|
|
4179
4982
|
static MG_ACT_REC_PREFIX = 1003;
|
|
@@ -4190,6 +4993,7 @@ class InternalInterface {
|
|
|
4190
4993
|
static MG_ACT_CYCLE_NEXT_DELETE_REC = 1018;
|
|
4191
4994
|
static MG_ACT_COMPUTE = 1020;
|
|
4192
4995
|
static MG_ACT_DUMMY = 1111;
|
|
4996
|
+
// INTERNAL EVENTS for WebClient
|
|
4193
4997
|
static MG_ACT_CTRL_FOCUS = 2001;
|
|
4194
4998
|
static MG_ACT_CTRL_MOUSEUP = 2002;
|
|
4195
4999
|
static MG_ACT_CTRL_KEYDOWN = 2003;
|
|
@@ -4199,12 +5003,13 @@ class InternalInterface {
|
|
|
4199
5003
|
static MG_ACT_ROW_DATA_CURR_PAGE = 2007;
|
|
4200
5004
|
static MG_ACT_DV_TO_GUI = 2008;
|
|
4201
5005
|
static MG_ACT_DISABLE_EVENTS = 2010;
|
|
5006
|
+
// toggle insert is temp 539 , it should match the code in online once it will be created.
|
|
4202
5007
|
static MG_ACT_TOGGLE_INSERT = 2011;
|
|
4203
5008
|
static MG_ACT_INCREMENTAL_LOCATE = 2017;
|
|
4204
5009
|
static MG_ACT_MOVE_TO_FIRST_CTRL = 2018;
|
|
4205
5010
|
static MG_ACT_SET_EXTERNAL_VALUE = 2019;
|
|
4206
5011
|
static MG_ACT_CTRL_FOCUS_ON_NON_MAGIC_CONTROL = 2020;
|
|
4207
|
-
static MG_ACT_FETCH_RECORDS_AHEAD_FROM_SERVER = 2021;
|
|
5012
|
+
static MG_ACT_FETCH_RECORDS_AHEAD_FROM_SERVER = 2021; // for paginated table, fetch records in background depending on PROP_TYPE_SERVER_READ_AHEAD
|
|
4208
5013
|
static BuiltinEvent(eventCode) {
|
|
4209
5014
|
return eventCode >= 1000 || eventCode === InternalInterface.MG_ACT_POST_REFRESH_BY_PARENT;
|
|
4210
5015
|
}
|
|
@@ -4223,11 +5028,14 @@ class OSEnvironment {
|
|
|
4223
5028
|
static TabSeq = "\t";
|
|
4224
5029
|
static getStackTrace() {
|
|
4225
5030
|
let ex = new Exception();
|
|
4226
|
-
ex.errorLevel++;
|
|
5031
|
+
ex.errorLevel++; // we need to remove the line which contains call to this method
|
|
4227
5032
|
return ex.StackTrace;
|
|
4228
5033
|
}
|
|
4229
5034
|
}
|
|
4230
5035
|
|
|
5036
|
+
/// <summary>
|
|
5037
|
+
/// The class is responsible to maintain the Request information while sending a request to server
|
|
5038
|
+
/// </summary>
|
|
4231
5039
|
class RequestInfo {
|
|
4232
5040
|
serverCallAt;
|
|
4233
5041
|
runtimeTaskTree = new List();
|
|
@@ -4261,9 +5069,16 @@ var LogType;
|
|
|
4261
5069
|
LogType[LogType["warning"] = 2] = "warning";
|
|
4262
5070
|
LogType[LogType["error"] = 3] = "error";
|
|
4263
5071
|
})(LogType || (LogType = {}));
|
|
5072
|
+
/// <summary>
|
|
5073
|
+
/// Logger class will take care of client side logging . It will check for various log levels and accordingly will write messages in log file.
|
|
5074
|
+
/// </summary>
|
|
5075
|
+
//@dynamic
|
|
4264
5076
|
class Logger {
|
|
4265
5077
|
static instance = null;
|
|
4266
|
-
LogLevel = 0;
|
|
5078
|
+
LogLevel = 0; // InternalLogLevel
|
|
5079
|
+
/// <summary>
|
|
5080
|
+
/// While writing the error messages in the file play the beep.
|
|
5081
|
+
/// </summary>
|
|
4267
5082
|
ShouldBeep = false;
|
|
4268
5083
|
static set Instance(value) {
|
|
4269
5084
|
Logger.instance = value;
|
|
@@ -4274,10 +5089,26 @@ class Logger {
|
|
|
4274
5089
|
}
|
|
4275
5090
|
return Logger.instance;
|
|
4276
5091
|
}
|
|
5092
|
+
/// <summary>
|
|
5093
|
+
/// Initialize logger
|
|
5094
|
+
/// </summary>
|
|
5095
|
+
/// <param name="logLevel"></param>
|
|
5096
|
+
/// <param name="internalLogSync"></param>
|
|
4277
5097
|
Initialize(logLevel, shouldBeep) {
|
|
4278
5098
|
try {
|
|
5099
|
+
// let logSync: LogSyncMode = LogSyncMode.Session;
|
|
4279
5100
|
this.LogLevel = logLevel;
|
|
4280
5101
|
this.ShouldBeep = shouldBeep;
|
|
5102
|
+
// TODO: implement
|
|
5103
|
+
// String strLogSync = internalLogSync;
|
|
5104
|
+
// if (!string.IsNullOrEmpty(strLogSync))
|
|
5105
|
+
// {
|
|
5106
|
+
// if (strLogSync.StartsWith("M", StringComparison.CurrentCultureIgnoreCase))
|
|
5107
|
+
// logSync = LogSyncMode.Message;
|
|
5108
|
+
// else if (strLogSync.StartsWith("F", StringComparison.CurrentCultureIgnoreCase))
|
|
5109
|
+
// logSync = LogSyncMode.Flush;
|
|
5110
|
+
// }
|
|
5111
|
+
//
|
|
4281
5112
|
}
|
|
4282
5113
|
catch (e) {
|
|
4283
5114
|
this.WriteDevToLog("ClientManager.init(): " + e.Message);
|
|
@@ -4301,6 +5132,9 @@ class Logger {
|
|
|
4301
5132
|
ShouldLogExtendedServerRelatedMessages() {
|
|
4302
5133
|
return (Logger.Instance.ShouldLog(Logger_LogLevels.ServerMessages) || Logger.Instance.ShouldLog(Logger_LogLevels.Support) || Logger.Instance.ShouldLog(Logger_LogLevels.Development)) && this.LogLevel !== Logger_LogLevels.Basic;
|
|
4303
5134
|
}
|
|
5135
|
+
/// <summary></summary>
|
|
5136
|
+
/// <param name="msg"></param>
|
|
5137
|
+
/// <param name="openIfNecessary">open the log file if not opened yet</param>
|
|
4304
5138
|
WriteToLog(msg, openIfNecessary, logType = LogType.info) {
|
|
4305
5139
|
if (this.LogLevel > Logger_LogLevels.None || openIfNecessary) {
|
|
4306
5140
|
msg = NString.Format("{0} {1}", (this.LogLevel === Logger_LogLevels.Basic) ? new Date().toISOString() : DateTimeUtils.ToString(DateTime.Now, XMLConstants.ERROR_LOG_TIME_FORMAT, this), msg);
|
|
@@ -4316,16 +5150,26 @@ class Logger {
|
|
|
4316
5150
|
}
|
|
4317
5151
|
}
|
|
4318
5152
|
}
|
|
5153
|
+
/// <summary>
|
|
5154
|
+
/// write a server access to the log
|
|
5155
|
+
/// </summary>
|
|
5156
|
+
/// <param name="msg">the message to write to the log</param>
|
|
4319
5157
|
WriteServerToLog(msg) {
|
|
4320
5158
|
if (this.ShouldLogServerRelatedMessages()) {
|
|
4321
5159
|
this.WriteToLog(NString.Format("Server, Thread={0}: ", Thread.CurrentThread.ManagedThreadId) + msg, false, LogType.info);
|
|
4322
5160
|
}
|
|
4323
5161
|
}
|
|
5162
|
+
/// <summary>
|
|
5163
|
+
/// write a server access to the log, including the content
|
|
5164
|
+
/// </summary>
|
|
5165
|
+
/// <param name="msg">the message to write to the log</param>
|
|
4324
5166
|
WriteServerMessagesToLog(msg) {
|
|
4325
5167
|
if (this.ShouldLogExtendedServerRelatedMessages()) {
|
|
4326
5168
|
this.WriteToLog("Server#: " + msg, false, LogType.info);
|
|
4327
5169
|
}
|
|
4328
5170
|
}
|
|
5171
|
+
/// <summary>Write a QC message to the log</summary>
|
|
5172
|
+
/// <param name="msg">the message to write to the log</param>
|
|
4329
5173
|
WriteSupportToLog(msg, skipLine) {
|
|
4330
5174
|
if (this.LogLevel >= Logger_LogLevels.Support && this.LogLevel !== Logger_LogLevels.Basic) {
|
|
4331
5175
|
if (skipLine) {
|
|
@@ -4336,16 +5180,31 @@ class Logger {
|
|
|
4336
5180
|
}
|
|
4337
5181
|
}
|
|
4338
5182
|
}
|
|
5183
|
+
/// <summary>
|
|
5184
|
+
/// write a performance message to the log
|
|
5185
|
+
/// </summary>
|
|
5186
|
+
/// <param name="msg">the message to write to the log</param>
|
|
4339
5187
|
WriteGuiToLog(msg) {
|
|
4340
5188
|
if (this.LogLevel >= Logger_LogLevels.Gui && this.LogLevel !== Logger_LogLevels.Basic) {
|
|
4341
5189
|
this.WriteToLog(msg, false, LogType.info);
|
|
4342
5190
|
}
|
|
4343
5191
|
}
|
|
5192
|
+
/// <summary>
|
|
5193
|
+
/// write a developer message to the log
|
|
5194
|
+
/// </summary>
|
|
5195
|
+
/// <param name="msg">the message to write to the log</param>
|
|
4344
5196
|
WriteDevToLog(msg) {
|
|
4345
5197
|
if (this.LogLevel >= Logger_LogLevels.Development && this.LogLevel !== Logger_LogLevels.Basic) {
|
|
4346
5198
|
this.WriteToLog("DEV: " + msg, false, LogType.info);
|
|
4347
5199
|
}
|
|
4348
5200
|
}
|
|
5201
|
+
/// <summary>
|
|
5202
|
+
/// Writes a basic level entry to log
|
|
5203
|
+
/// </summary>
|
|
5204
|
+
/// <param name="messageDirection">message direction relative to the current module (RIA client). Can be either MessageEntering or MessageLeaving</param>
|
|
5205
|
+
/// <param name="statusCode">HTTP status code</param>
|
|
5206
|
+
/// <param name="contentLength">length of the http message</param>
|
|
5207
|
+
/// <param name="httpHeaders">HTTP headers</param>
|
|
4349
5208
|
WriteBasicToLog(messageDirection, contextID, sessionCounter, clientID, serverID, responseTime, statusCode, httpHeaders, contentLength) {
|
|
4350
5209
|
if (this.LogLevel === Logger_LogLevels.Basic) {
|
|
4351
5210
|
let text = httpHeaders;
|
|
@@ -4353,6 +5212,8 @@ class Logger {
|
|
|
4353
5212
|
text = NString.Replace(text, "\r\n", "|");
|
|
4354
5213
|
let arg_E4_0 = "RIA,{0}_{1},{2},{3},{4},{5},-,{6},{7},{8},{9},{10},{11}";
|
|
4355
5214
|
let expr_3E = new Array(12);
|
|
5215
|
+
// TODO : need to check How to handle Process class.
|
|
5216
|
+
// expr_3E[0] = Process.GetCurrentProcess().Id;
|
|
4356
5217
|
expr_3E[1] = Thread.CurrentThread.ManagedThreadId;
|
|
4357
5218
|
expr_3E[2] = new Date().toISOString();
|
|
4358
5219
|
expr_3E[3] = ((messageDirection === Logger_MessageDirection.MessageLeaving) ? "MSGL" : "MSGE");
|
|
@@ -4371,14 +5232,37 @@ class Logger {
|
|
|
4371
5232
|
console.log(value);
|
|
4372
5233
|
}
|
|
4373
5234
|
}
|
|
5235
|
+
/// <summary>
|
|
5236
|
+
/// Writes request information to log
|
|
5237
|
+
/// </summary>
|
|
5238
|
+
/// <param name="clientSession">The clientSession object to be logged</param>
|
|
4374
5239
|
WriteRequestInfoToLog(requestInfo, extraMessageStr) {
|
|
4375
5240
|
if (this.LogLevel === Logger_LogLevels.RequestInfo) {
|
|
5241
|
+
// Chrome debugger automatically recomputes logged objects.
|
|
5242
|
+
// Hence, clone the requestInfo object to print the details at the time of logging
|
|
4376
5243
|
console.log(extraMessageStr, RequestInfo.clone(requestInfo));
|
|
4377
5244
|
}
|
|
4378
5245
|
}
|
|
5246
|
+
/// <summary>
|
|
5247
|
+
/// Writes a request exception basic level entry to log
|
|
5248
|
+
/// </summary>
|
|
5249
|
+
/// <param name="contextID"></param>
|
|
5250
|
+
/// <param name="sessionCounter"></param>
|
|
5251
|
+
/// <param name="clientID"></param>
|
|
5252
|
+
/// <param name="serverID"></param>
|
|
5253
|
+
/// <param name="ex">the logged exception</param>
|
|
4379
5254
|
WriteBasicErrorToLog() {
|
|
4380
5255
|
Debug.Assert(this.LogLevel === Logger_LogLevels.Basic);
|
|
4381
|
-
|
|
5256
|
+
// TODO : Need to check how to handle Process
|
|
5257
|
+
// let value: string = NString.Format("RIA,{0}_{1},{2},{3},{4},{5},-,{6},{7},-,-,-,{8} {9}", [
|
|
5258
|
+
// Process.GetCurrentProcess().Id, Thread.CurrentThread.ManagedThreadId, DateTime.UtcNow.ToString("yyyy-MM-ddTHH:mm:ss.fffffffZ"), "RES", contextID, sessionCounter, clientID, serverID, ex.GetType(), ex.Message
|
|
5259
|
+
// ]);
|
|
5260
|
+
// NConsole.WriteLine(value);
|
|
5261
|
+
}
|
|
5262
|
+
/// <summary>
|
|
5263
|
+
/// Write an error to the log
|
|
5264
|
+
/// </summary>
|
|
5265
|
+
/// <param name="msg">the message to write to the log</param>
|
|
4382
5266
|
WriteErrorToLog(msg) {
|
|
4383
5267
|
this.WriteToLog("MagicWeb [ERROR]: " + StrUtil.getConsoleErorString(msg), true, LogType.error);
|
|
4384
5268
|
}
|
|
@@ -4458,6 +5342,9 @@ class Logger {
|
|
|
4458
5342
|
}
|
|
4459
5343
|
this.WriteToLog(stringBuilder.ToString(), true);
|
|
4460
5344
|
}
|
|
5345
|
+
/// <summary>
|
|
5346
|
+
/// Flush the log writer.
|
|
5347
|
+
/// </summary>
|
|
4461
5348
|
Flush() {
|
|
4462
5349
|
}
|
|
4463
5350
|
constructor() {
|
|
@@ -4651,6 +5538,8 @@ class MsgInterface {
|
|
|
4651
5538
|
static RC_ERROR_ILLEGAL_RETURN_VAL_ATTR_TYPE = "RC_ERROR_ILLEGAL_RETURN_VAL_ATTR_TYPE";
|
|
4652
5539
|
static STR_ERR_WEBCLIENT_PROGRAM_RELOADED = "STR_ERR_WEBCLIENT_PROGRAM_RELOADED";
|
|
4653
5540
|
static STR_ERR_EXECUTED_PROGRAM_CHANGED = "STR_ERR_EXECUTED_PROGRAM_CHANGED";
|
|
5541
|
+
static STR_ERR_MAX_ALLOWED_LENGTH = "STR_ERR_MAX_ALLOWED_LENGTH";
|
|
5542
|
+
static STR_ERR_MAX_ALLOWED_VALUE = "STR_ERR_MAX_ALLOWED_VALUE";
|
|
4654
5543
|
static DefaultMessages = [
|
|
4655
5544
|
new DefaultMsgDetails("STR_ERR_NUM", "Invalid number"), new DefaultMsgDetails("STR_ERR_DATE", "Invalid date"), new DefaultMsgDetails("STR_ERR_TIME", "Invalid time"), new DefaultMsgDetails("MONTHS_PTR", "January February March April May June July August September October November December"), new DefaultMsgDetails("DAYS_PTR", "Sunday Monday Tuesday Wednesday Thursday Friday Saturday"), new DefaultMsgDetails("STR_ERR_NEGETIVE", "Control value must be non-negative"), new DefaultMsgDetails("STR_RNG_TXT", "Valid control input range is:"), new DefaultMsgDetails("EDT_ERR_STR_1", "Numeric format is limited to %d.%d digits"), new DefaultMsgDetails("STR_ERR_PIPE_CONNECTION", "The connection to the runtime engine was lost. Process ID "), new DefaultMsgDetails("FMERROR_STR_BAD_NAME", "Invalid data source name:"), new DefaultMsgDetails("FMERROR_STR_BAD_DAMAGED", "Damaged data source:"), new DefaultMsgDetails("FMERROR_STR_BAD_BADCREATE", "Create error:"), new DefaultMsgDetails("FMERROR_STR_FILE_LOCKED", "Unable to lock the data source:"), new DefaultMsgDetails("FMERROR_STR_BAD_UNEXPECTED", "Unexpected error, data source:"), new DefaultMsgDetails("FMERROR_STR_BAD_SERVER_NOTFOUND", "Server not found, data source:"), new DefaultMsgDetails("FMERROR_STR_BAD_SERVER_INIT_FAILED", "Server initialization failed, data source:"), new DefaultMsgDetails("FMERROR_STR_UNLOCKED", "Releasing failed, data source:"), new DefaultMsgDetails("FMERROR_STR_BAD_DB_INIT_FAILED", "Database initialization error, data source:"), new DefaultMsgDetails("FMERROR_STR_BAD_LOCK_OPEN", "Failed to open lock file, data source:"),
|
|
4656
5545
|
new DefaultMsgDetails("FMERROR_STR_BAD_BADOPEN", "Failed to open, data source:"), new DefaultMsgDetails("FMERROR_STR_BAD_BADDEF", "Definition mismatch, data source:"), new DefaultMsgDetails("FMERROR_STR_DUP_KEY", "Duplicate index, data source:"), new DefaultMsgDetails("FMERROR_STR_COMM_LOADED", "Communication Gateway not loaded, data source:"), new DefaultMsgDetails("FMERROR_STR_COMM_CONNECT", "Failed to connect to server, data source:"), new DefaultMsgDetails("FMERROR_STR_READONLY", "Cannot modify Read Only, data source:"), new DefaultMsgDetails("FMERROR_STR_BAD_BADCLOSE", "Failed to close, data source:"), new DefaultMsgDetails("FMERROR_STR_REC_LOCKED", "Waiting for locked row, data source:"), new DefaultMsgDetails("FMERROR_STR_TRANS_OPEN", "Failed to open transaction, data source:"), new DefaultMsgDetails("FMERROR_STR_COMMIT", "Failed to commit transaction"), new DefaultMsgDetails("FMERROR_STR_ABORT", "Failed to abort transaction"), new DefaultMsgDetails("FMERROR_STR_RSRC_LOCKED", "Waiting for lock in database:"), new DefaultMsgDetails("FMERROR_STR_NODEF", "Database definition cannot be loaded, data source:"), new DefaultMsgDetails("FMERROR_STR_DEADLOCK", "Deadlock error, data source:"), new DefaultMsgDetails("FMERROR_STR_DB_PROT", "Exceeded database protection limits, data source:"), new DefaultMsgDetails("FMERROR_STR_OWNR_ALRDY_SET", "Access Key already set, data source:"), new DefaultMsgDetails("FMERROR_STR_INVALID_OWNR", "Invalid Access Key, data source:"), new DefaultMsgDetails("FMERROR_STR_CLR_OWNR_FAIL", "Failed to clear Access Key, data source:"), new DefaultMsgDetails("FMERROR_STR_NO_DATABASE", "Unknown database, data source:"), new DefaultMsgDetails("FMERROR_STR_DBMS_ALTER_FAIL", "Warning - Database failed to alter, data source:"),
|
|
@@ -4662,17 +5551,20 @@ class MsgInterface {
|
|
|
4662
5551
|
new DefaultMsgDetails("ERR_CANNOT_HANDLE_WEB_REQUEST", "Web client requests cannot be handled when the online MDI is open"),
|
|
4663
5552
|
new DefaultMsgDetails("STR_MDI_FRAME_MISMATCH", "The selected MDI Frame form cannot be used for the current task"), new DefaultMsgDetails("CHK_ERR_OFFLINE_NOT_SUPPORT_FRAME_INTERFACE", "Frames interface is not supported in an offline task"), new DefaultMsgDetails("STR_USER_ID", "User ID:"), new DefaultMsgDetails("STR_PASSWORD", "Password:"),
|
|
4664
5553
|
new DefaultMsgDetails("STR_LOGON_PARAMETERS", "Logon Parameters"), new DefaultMsgDetails("STR_LOGON_CAPTION", "Logon"), new DefaultMsgDetails("STR_LOGON_INSTRUCTION", "Please enter your user ID and password."), new DefaultMsgDetails("STR_GENERIC_ERROR_MESSAGE", "An error occurred (%d). Please contact your system administrator."), new DefaultMsgDetails("STR_GENERIC_ERROR_CONNECTION_PROBLEM_TITLE", "Connection problem:"), new DefaultMsgDetails("STR_GENERIC_ERROR_CONNECTION_PROBLEM_MESSAGE", "Try to reconnect?"), new DefaultMsgDetails("FMERROR_STR_TRANS_OPEN_FAILED", "The transaction was already opened by another task"), new DefaultMsgDetails("STR_ERR_CANNOT_CALL_OFFLINE_BYNAME_OR_BYEXP", "Offline programs cannot be called using the Call By Name or Call By Expression operations"), new DefaultMsgDetails("RT_STR_DELETE_MODE_WITHOUT_MAINSOURCE_NOTALLOWED", "Deleted task mode is not allowed without main source"), new DefaultMsgDetails("RC_ERROR_INCOMPATIBLE_DATASOURCES", "Failed to update the local data. Please clear the application cache or reinstall the application."), new DefaultMsgDetails("RC_ERROR_INVALID_SOURCES", "Failed to update the application."), new DefaultMsgDetails("RC_ERROR_OFFLINE_NEXT_EXECUTION_INVALID_SOURCES", "Failed to start the application. Please restart while the application is connected to the server."), new DefaultMsgDetails("RC_ERR_ANDROID_LOAD_FROM_URL", "Cannot access the server."), new DefaultMsgDetails("STR_CLIENT_DB_DEL_OPERATION_FAILED", "ClientDbDel opeartion failed."), new DefaultMsgDetails("STR_DATAVIEW_TO_DATASOURCE_OPERATION_FAILED", "DataViewToDataSource operation failed."), new DefaultMsgDetails("STR_CLIENT_DB_DISCONNECT_DATASOURCE_OPEN", "Failed to disconnect, data source is open."), new DefaultMsgDetails("STR_CLIENT_DB_DISCONNECT_DATASOURCE_NOT_EXIST", "Failed to disconnect, database does not exist."), new DefaultMsgDetails("FMERROR_STR_INVALID_PASSWORD", "Invalid Password, data source:"), new DefaultMsgDetails("STR_MOBILE_TAB_CONTROL_CANNOT_BE_USED", "Tab control cannot be used in a container control."), new DefaultMsgDetails("STR_MOBILE_CONTROLS_CANNOT_BE_OUTSIDE_TAB", "Controls cannot be placed outside a tab control."),
|
|
4665
|
-
new DefaultMsgDetails("STR_MOBILE_TAB_CONTROL_LAYER_0", "Controls cannot be linked to layer 0 of the tab control."), new DefaultMsgDetails("STR_MOBILE_TAB_DISPLAY_LIST_ERROR", "The number of entries in the Display List property must be zero or match the number of entries in the Items List property."), new DefaultMsgDetails("RC_ERROR_ARG_TYPE_STRING_NUMBER_MISMATCH", "The number of characters in the argument type string does not match the number of total arguments"), new DefaultMsgDetails("RC_ERROR_ILLEGAL_ARG_ATTR_TYPE", "Illegal argument attribute type"), new DefaultMsgDetails("RC_ERROR_ILLEGAL_RETURN_VAL_ATTR_TYPE", "Illegal return value attribute type"), new DefaultMsgDetails("STR_ERR_WEBCLIENT_PROGRAM_RELOADED", "Changes were done at the server side. Browser will be refreshed in order to get the latest changes."), new DefaultMsgDetails("STR_ERR_EXECUTED_PROGRAM_CHANGED", "Executed program changed at the server side. Browser will be refreshed in order to get the latest changes.")
|
|
5554
|
+
new DefaultMsgDetails("STR_MOBILE_TAB_CONTROL_LAYER_0", "Controls cannot be linked to layer 0 of the tab control."), new DefaultMsgDetails("STR_MOBILE_TAB_DISPLAY_LIST_ERROR", "The number of entries in the Display List property must be zero or match the number of entries in the Items List property."), new DefaultMsgDetails("RC_ERROR_ARG_TYPE_STRING_NUMBER_MISMATCH", "The number of characters in the argument type string does not match the number of total arguments"), new DefaultMsgDetails("RC_ERROR_ILLEGAL_ARG_ATTR_TYPE", "Illegal argument attribute type"), new DefaultMsgDetails("RC_ERROR_ILLEGAL_RETURN_VAL_ATTR_TYPE", "Illegal return value attribute type"), new DefaultMsgDetails("STR_ERR_WEBCLIENT_PROGRAM_RELOADED", "Changes were done at the server side. Browser will be refreshed in order to get the latest changes."), new DefaultMsgDetails("STR_ERR_EXECUTED_PROGRAM_CHANGED", "Executed program changed at the server side. Browser will be refreshed in order to get the latest changes."), new DefaultMsgDetails("STR_ERR_MAX_ALLOWED_LENGTH", "Max length allowed is :"), new DefaultMsgDetails("STR_ERR_MAX_ALLOWED_VALUE", "Max value allowed is :")
|
|
4666
5555
|
];
|
|
4667
5556
|
constructor() {
|
|
4668
5557
|
}
|
|
4669
5558
|
}
|
|
4670
5559
|
|
|
5560
|
+
/// <summary> implementation of a general queue</summary>
|
|
4671
5561
|
class Queue {
|
|
4672
5562
|
_queueVec = null;
|
|
5563
|
+
/// <summary> </summary>
|
|
4673
5564
|
constructor() {
|
|
4674
5565
|
this._queueVec = new List();
|
|
4675
5566
|
}
|
|
5567
|
+
/// <summary> returns the first object in the queue</summary>
|
|
4676
5568
|
get() {
|
|
4677
5569
|
let returnValue = null;
|
|
4678
5570
|
if (this._queueVec.length > 0) {
|
|
@@ -4681,15 +5573,20 @@ class Queue {
|
|
|
4681
5573
|
}
|
|
4682
5574
|
return returnValue;
|
|
4683
5575
|
}
|
|
5576
|
+
/// <summary> add an object to the end of the queue</summary>
|
|
5577
|
+
/// <param name="obj">the object to add
|
|
4684
5578
|
put(obj) {
|
|
4685
5579
|
this._queueVec.push(obj);
|
|
4686
5580
|
}
|
|
5581
|
+
/// <summary> remove all the objects from the queue</summary>
|
|
4687
5582
|
clear() {
|
|
4688
5583
|
this._queueVec.Clear();
|
|
4689
5584
|
}
|
|
5585
|
+
/// <summary> returns true if the queue is empty</summary>
|
|
4690
5586
|
isEmpty() {
|
|
4691
5587
|
return this._queueVec.length === 0;
|
|
4692
5588
|
}
|
|
5589
|
+
/// <summary> returns size of the queue</summary>
|
|
4693
5590
|
Size() {
|
|
4694
5591
|
return this._queueVec.length;
|
|
4695
5592
|
}
|
|
@@ -4729,7 +5626,15 @@ class Randomizer {
|
|
|
4729
5626
|
}
|
|
4730
5627
|
}
|
|
4731
5628
|
|
|
5629
|
+
/// <summary>
|
|
5630
|
+
/// type checking for enum 'StorageAttribute'
|
|
5631
|
+
/// </summary>
|
|
4732
5632
|
class StorageAttributeCheck {
|
|
5633
|
+
/// <summary>
|
|
5634
|
+
/// is the both types belong to the same inner data types
|
|
5635
|
+
/// </summary>
|
|
5636
|
+
/// <param name = "type1">data type</param>
|
|
5637
|
+
/// <param name = "type2">data type</param>
|
|
4733
5638
|
static isTheSameType(type1, type2) {
|
|
4734
5639
|
return type1 === type2 || (StorageAttributeCheck.isTypeNumeric(type1) && StorageAttributeCheck.isTypeNumeric(type2)) || (StorageAttributeCheck.isTypeLogical(type1) && StorageAttributeCheck.isTypeLogical(type2)) || (StorageAttributeCheck.IsTypeAlphaOrUnicode(type1) && StorageAttributeCheck.IsTypeAlphaOrUnicode(type2)) || (StorageAttributeCheck.isTypeBlob(type1) && StorageAttributeCheck.isTypeBlob(type2)) || (StorageAttributeCheck.isTypeDotNet(type1) && StorageAttributeCheck.isTypeDotNet(type2));
|
|
4735
5640
|
}
|
|
@@ -4739,18 +5644,36 @@ class StorageAttributeCheck {
|
|
|
4739
5644
|
static isTypeAlpha(type) {
|
|
4740
5645
|
return type === StorageAttribute.ALPHA || type === StorageAttribute.MEMO;
|
|
4741
5646
|
}
|
|
5647
|
+
/// <summary>
|
|
5648
|
+
/// is the both types belong to the NUMERIC inner type
|
|
5649
|
+
/// </summary>
|
|
4742
5650
|
static isTypeNumeric(type) {
|
|
4743
5651
|
return type === StorageAttribute.DATE || type === StorageAttribute.TIME || type === StorageAttribute.NUMERIC;
|
|
4744
5652
|
}
|
|
5653
|
+
/// <summary>
|
|
5654
|
+
/// is the both types belong to the LOGICAL inner type
|
|
5655
|
+
/// </summary>
|
|
4745
5656
|
static isTypeLogical(type) {
|
|
4746
5657
|
return type === StorageAttribute.BOOLEAN;
|
|
4747
5658
|
}
|
|
5659
|
+
/// <summary>
|
|
5660
|
+
/// is the type is DOTNET
|
|
5661
|
+
/// </summary>
|
|
4748
5662
|
static isTypeDotNet(type) {
|
|
4749
5663
|
return type === StorageAttribute.DOTNET;
|
|
4750
5664
|
}
|
|
5665
|
+
/// <summary>
|
|
5666
|
+
/// is the type ALPHA or UNICODE
|
|
5667
|
+
/// </summary>
|
|
5668
|
+
/// <param name = "type">data type</param>
|
|
4751
5669
|
static IsTypeAlphaOrUnicode(type) {
|
|
4752
5670
|
return type === StorageAttribute.ALPHA || type === StorageAttribute.UNICODE;
|
|
4753
5671
|
}
|
|
5672
|
+
/// <summary>
|
|
5673
|
+
/// is the inner type ALPHA or UNICODE
|
|
5674
|
+
/// </summary>
|
|
5675
|
+
/// <param name = "type1">data type</param>
|
|
5676
|
+
/// <param name = "type2">data type</param>
|
|
4754
5677
|
static StorageFldAlphaOrUnicode(type1, type2) {
|
|
4755
5678
|
return StorageAttributeCheck.IsTypeAlphaOrUnicode(type1) && StorageAttributeCheck.IsTypeAlphaOrUnicode(type2);
|
|
4756
5679
|
}
|
|
@@ -4766,6 +5689,12 @@ class StorageAttributeCheck {
|
|
|
4766
5689
|
return ((type1AlphaOrUnicode && type2Blob) || (type2AlphaOrUnicode && type1Blob));
|
|
4767
5690
|
}
|
|
4768
5691
|
}
|
|
5692
|
+
/// <summary>
|
|
5693
|
+
/// Check if types are compatible or not.
|
|
5694
|
+
/// </summary>
|
|
5695
|
+
/// <param name="sourceAttribute"></param>
|
|
5696
|
+
/// <param name="destinationAttribute"></param>
|
|
5697
|
+
/// <returns></returns>
|
|
4769
5698
|
static IsTypeCompatibile(sourceAttribute, destinationAttribute) {
|
|
4770
5699
|
let isTypeCompatible = false;
|
|
4771
5700
|
switch (sourceAttribute) {
|
|
@@ -4812,22 +5741,39 @@ class StorageAttributeCheck {
|
|
|
4812
5741
|
}
|
|
4813
5742
|
}
|
|
4814
5743
|
|
|
5744
|
+
/// <summary>
|
|
5745
|
+
/// Helper class for synchronized execution.
|
|
5746
|
+
/// It works by creating a promise and then waiting for the promise to be completed
|
|
5747
|
+
/// </summary>
|
|
5748
|
+
// @dynamic
|
|
4815
5749
|
class SyncExecutionHelper {
|
|
4816
5750
|
static _instance = null;
|
|
5751
|
+
/// <summary>
|
|
5752
|
+
/// get instance of SyncExecutionHelper
|
|
5753
|
+
/// </summary>
|
|
4817
5754
|
static get Instance() {
|
|
4818
5755
|
if (SyncExecutionHelper._instance === null)
|
|
4819
5756
|
SyncExecutionHelper._instance = new SyncExecutionHelper();
|
|
4820
5757
|
return SyncExecutionHelper._instance;
|
|
4821
5758
|
}
|
|
5759
|
+
// resolver is caller when promise is fullfilled
|
|
4822
5760
|
resolver = null;
|
|
5761
|
+
/// <summary>
|
|
5762
|
+
/// To wait, create a promise and add wait for it to complete
|
|
5763
|
+
/// </summary>
|
|
4823
5764
|
Wait() {
|
|
5765
|
+
// Logger.Instance.WriteDevToLog("SyncExecutionHelper.Wait()");
|
|
4824
5766
|
return new Promise((resolve) => {
|
|
4825
5767
|
this.resolver = resolve;
|
|
4826
5768
|
}).then();
|
|
4827
5769
|
}
|
|
5770
|
+
/// <summary>
|
|
5771
|
+
/// To resume call the resolver
|
|
5772
|
+
/// </summary>
|
|
4828
5773
|
Pulse() {
|
|
4829
5774
|
let resolver = this.resolver;
|
|
4830
5775
|
if (resolver != null) {
|
|
5776
|
+
// Logger.Instance.WriteDevToLog("SyncExecutionHelper.Pulse()");
|
|
4831
5777
|
resolver();
|
|
4832
5778
|
}
|
|
4833
5779
|
}
|
|
@@ -4835,6 +5781,12 @@ class SyncExecutionHelper {
|
|
|
4835
5781
|
|
|
4836
5782
|
const MAX_GENGO = 6;
|
|
4837
5783
|
class UtilDateJpn {
|
|
5784
|
+
/// <summary>
|
|
5785
|
+
/// JPN: Japanese date picture support
|
|
5786
|
+
/// Utility Class for Japanese date
|
|
5787
|
+
/// </summary>
|
|
5788
|
+
/// <author> Toshiro Nakayoshi (MSJ)
|
|
5789
|
+
/// </author>
|
|
4838
5790
|
static _instance = null;
|
|
4839
5791
|
static JweekStr = [
|
|
4840
5792
|
" ", "日曜日", "月曜日", "火曜日", "水曜日", "木曜日", "金曜日", "土曜日"
|
|
@@ -4860,10 +5812,11 @@ class UtilDateJpn {
|
|
|
4860
5812
|
[1926, 12, 25, 359],
|
|
4861
5813
|
[1989, 1, 8, 8],
|
|
4862
5814
|
[2019, 5, 1, 121],
|
|
4863
|
-
[0, 0, 0, 0],
|
|
5815
|
+
[0, 0, 0, 0], // reserve for extra gengo x 3
|
|
4864
5816
|
[0, 0, 0, 0],
|
|
4865
5817
|
[0, 0, 0, 0]
|
|
4866
5818
|
];
|
|
5819
|
+
// ---- gengo (the name of an era) ---------------------------------------
|
|
4867
5820
|
MaxGengo = MAX_GENGO;
|
|
4868
5821
|
static getInstance() {
|
|
4869
5822
|
if (UtilDateJpn._instance === null) {
|
|
@@ -4888,6 +5841,18 @@ class UtilDateJpn {
|
|
|
4888
5841
|
}
|
|
4889
5842
|
return UtilDateJpn.JmonthStr[month];
|
|
4890
5843
|
}
|
|
5844
|
+
/// <summary>
|
|
5845
|
+
/// Convert a year (A.D.) into Japanese year of an era
|
|
5846
|
+
/// This method is modeled after "date_jpn_year_ofs" function in
|
|
5847
|
+
/// "\mglocal\jpn\jpndate_jpn.cpp".
|
|
5848
|
+
/// </summary>
|
|
5849
|
+
/// <param name = "intYear:">year (A.D.)
|
|
5850
|
+
/// </param>
|
|
5851
|
+
/// <param name = "intDoy:">DOY
|
|
5852
|
+
/// </param>
|
|
5853
|
+
/// <returns> year of an era.
|
|
5854
|
+
/// if either param is invalid, it returns 0.
|
|
5855
|
+
/// </returns>
|
|
4891
5856
|
date_jpn_year_ofs(intYear, intDoy) {
|
|
4892
5857
|
let result;
|
|
4893
5858
|
if (intYear < 1 || intDoy < 1) {
|
|
@@ -4905,6 +5870,20 @@ class UtilDateJpn {
|
|
|
4905
5870
|
}
|
|
4906
5871
|
return result;
|
|
4907
5872
|
}
|
|
5873
|
+
/// <summary>
|
|
5874
|
+
/// Convert a year (A.D.) into a name of a Japanese era
|
|
5875
|
+
/// This method is modeled after "date_jpn_yr_2_a" function in
|
|
5876
|
+
/// "\mglocal\jpn\jpndate_jpn.cpp".
|
|
5877
|
+
/// </summary>
|
|
5878
|
+
/// <param name = "intYear:">year (A.D.)
|
|
5879
|
+
/// </param>
|
|
5880
|
+
/// <param name = "intDoy:">DOY
|
|
5881
|
+
/// </param>
|
|
5882
|
+
/// <param name = "isKanji:">return a full name (true) or the first letter (false).
|
|
5883
|
+
/// </param>
|
|
5884
|
+
/// <returns> name of an era
|
|
5885
|
+
/// if either param is invalid, it returns "?".
|
|
5886
|
+
/// </returns>
|
|
4908
5887
|
date_jpn_yr_2_a(intYear, intDoy, isKanji) {
|
|
4909
5888
|
let num;
|
|
4910
5889
|
if (intYear < 1 || intDoy < 1) {
|
|
@@ -4928,6 +5907,17 @@ class UtilDateJpn {
|
|
|
4928
5907
|
}
|
|
4929
5908
|
return result;
|
|
4930
5909
|
}
|
|
5910
|
+
/// <summary>
|
|
5911
|
+
/// Get the first year (A.D.) of a specified Japanese era
|
|
5912
|
+
/// This method is modeled after "date_jpn_yr_4_a" function in
|
|
5913
|
+
/// "\mglocal\jpn\jpndate_jpn.cpp".
|
|
5914
|
+
/// </summary>
|
|
5915
|
+
/// <param name = "ucp_str:">name of a specified Japanese era
|
|
5916
|
+
/// </param>
|
|
5917
|
+
/// <param name = "s_len:">length (the number of bytes) of ucp_str
|
|
5918
|
+
/// </param>
|
|
5919
|
+
/// <returns> year (A.D.)
|
|
5920
|
+
/// </returns>
|
|
4931
5921
|
date_jpn_yr_4_a(ucp_str, s_len) {
|
|
4932
5922
|
let i = this.MaxGengo - 1;
|
|
4933
5923
|
if (s_len > 0) {
|
|
@@ -4966,6 +5956,17 @@ class UtilDateJpn {
|
|
|
4966
5956
|
}
|
|
4967
5957
|
return result;
|
|
4968
5958
|
}
|
|
5959
|
+
/// <summary>
|
|
5960
|
+
/// Get the name of an era in date string
|
|
5961
|
+
/// </summary>
|
|
5962
|
+
/// <param name = "strDate:">string of input strDate
|
|
5963
|
+
/// </param>
|
|
5964
|
+
/// <param name = "strPicture:">string of picture
|
|
5965
|
+
/// </param>
|
|
5966
|
+
/// <param name = "intStartPos:">start position to search
|
|
5967
|
+
/// </param>
|
|
5968
|
+
/// <returns> name of an era
|
|
5969
|
+
/// </returns>
|
|
4969
5970
|
static getEraNameStrInDate(strDate, strPicture, intStartPos) {
|
|
4970
5971
|
let result = null;
|
|
4971
5972
|
let intPicIdxOfs = 0;
|
|
@@ -4984,6 +5985,7 @@ class UtilDateJpn {
|
|
|
4984
5985
|
intLetters = 2;
|
|
4985
5986
|
}
|
|
4986
5987
|
else {
|
|
5988
|
+
// If "strDate" contains DBCS, the position of "strPicture" has to skip next index.
|
|
4987
5989
|
if (i < strDate.length) {
|
|
4988
5990
|
if (!UtilStrByteMode.isHalfWidth(strDate[i]) && UtilStrByteMode.isHalfWidth(strPicture[i + intPicIdxOfs])) {
|
|
4989
5991
|
intPicIdxOfs = intPicIdxOfs + 1;
|
|
@@ -4995,10 +5997,19 @@ class UtilDateJpn {
|
|
|
4995
5997
|
}
|
|
4996
5998
|
}
|
|
4997
5999
|
result = strDate.substr(i, intLetters);
|
|
4998
|
-
break;
|
|
6000
|
+
break; // exit loop
|
|
4999
6001
|
}
|
|
5000
6002
|
return result;
|
|
5001
6003
|
}
|
|
6004
|
+
/// <summary>
|
|
6005
|
+
/// Get the length of the name of an era in picture
|
|
6006
|
+
/// </summary>
|
|
6007
|
+
/// <param name = "strPicture">string of picture
|
|
6008
|
+
/// </param>
|
|
6009
|
+
/// <param name = "intStartPos">start position to search
|
|
6010
|
+
/// </param>
|
|
6011
|
+
/// <returns> length of the name (the number of bytes)
|
|
6012
|
+
/// </returns>
|
|
5002
6013
|
static getEraNameLenInPicture(strPicture, intStartPos) {
|
|
5003
6014
|
let intLetters = 0;
|
|
5004
6015
|
for (let i = intStartPos; i < strPicture.length; i = i + 1) {
|
|
@@ -5021,6 +6032,15 @@ class UtilDateJpn {
|
|
|
5021
6032
|
}
|
|
5022
6033
|
return intLetters;
|
|
5023
6034
|
}
|
|
6035
|
+
/// <summary>
|
|
6036
|
+
/// Get the start year of an era in picture
|
|
6037
|
+
/// </summary>
|
|
6038
|
+
/// <param name = "strDate:">string of input strDate
|
|
6039
|
+
/// </param>
|
|
6040
|
+
/// <param name = "strPicture:">string of picture
|
|
6041
|
+
/// </param>
|
|
6042
|
+
/// <returns> start year of the era
|
|
6043
|
+
/// </returns>
|
|
5024
6044
|
getStartYearOfEra(strDate, strPicture) {
|
|
5025
6045
|
let eraNameStrInDate = UtilDateJpn.getEraNameStrInDate(strDate, strPicture, 0);
|
|
5026
6046
|
let result;
|
|
@@ -5039,7 +6059,13 @@ class UtilDateJpn {
|
|
|
5039
6059
|
}
|
|
5040
6060
|
return result;
|
|
5041
6061
|
}
|
|
6062
|
+
/// <summary> Add extra Gengo data into the Gengo tables</summary>
|
|
6063
|
+
/// <param name="strExtraGengo:">
|
|
6064
|
+
/// </param>
|
|
6065
|
+
/// <returns>
|
|
6066
|
+
/// </returns>
|
|
5042
6067
|
addExtraGengo(strExtraGengo) {
|
|
6068
|
+
// e.g. strExtraGengo = "2012/04/01,092,AaABCD;2013/04/01,091,WwWXYZ;"
|
|
5043
6069
|
let strGengoInfo = strExtraGengo.split(';');
|
|
5044
6070
|
for (let i = 0; i < strGengoInfo.length; i = i + 1) {
|
|
5045
6071
|
if (strGengoInfo[i].length > 0) {
|
|
@@ -5047,13 +6073,13 @@ class UtilDateJpn {
|
|
|
5047
6073
|
if (strTok.length === 3 && strTok[0].length > 0 && strTok[1].length > 0 && strTok[2].length > 0) {
|
|
5048
6074
|
let strDate = strTok[0].split('/');
|
|
5049
6075
|
if (strDate.length === 3 && strDate[0].length > 0 && strDate[1].length > 0 && strDate[2].length > 0) {
|
|
5050
|
-
UtilDateJpn.GengoStr[MAX_GENGO + i][0] = strTok[2].substr(0, 1);
|
|
5051
|
-
UtilDateJpn.GengoStr[MAX_GENGO + i][1] = strTok[2].substr(1, 1);
|
|
5052
|
-
UtilDateJpn.GengoStr[MAX_GENGO + i][2] = strTok[2].substr(2);
|
|
5053
|
-
UtilDateJpn.StartDayOfGengo[MAX_GENGO + i][0] = NNumber.Parse(strDate[0]);
|
|
5054
|
-
UtilDateJpn.StartDayOfGengo[MAX_GENGO + i][1] = NNumber.Parse(strDate[1]);
|
|
5055
|
-
UtilDateJpn.StartDayOfGengo[MAX_GENGO + i][2] = NNumber.Parse(strDate[2]);
|
|
5056
|
-
UtilDateJpn.StartDayOfGengo[MAX_GENGO + i][3] = NNumber.Parse(strTok[1]);
|
|
6076
|
+
UtilDateJpn.GengoStr[MAX_GENGO + i][0] = strTok[2].substr(0, 1); // symbol name (upper case): A
|
|
6077
|
+
UtilDateJpn.GengoStr[MAX_GENGO + i][1] = strTok[2].substr(1, 1); // symbol name (lower case): a
|
|
6078
|
+
UtilDateJpn.GengoStr[MAX_GENGO + i][2] = strTok[2].substr(2); // gengo name: ABCD
|
|
6079
|
+
UtilDateJpn.StartDayOfGengo[MAX_GENGO + i][0] = NNumber.Parse(strDate[0]); // start year: 2012
|
|
6080
|
+
UtilDateJpn.StartDayOfGengo[MAX_GENGO + i][1] = NNumber.Parse(strDate[1]); // start month: 4
|
|
6081
|
+
UtilDateJpn.StartDayOfGengo[MAX_GENGO + i][2] = NNumber.Parse(strDate[2]); // start day: 1
|
|
6082
|
+
UtilDateJpn.StartDayOfGengo[MAX_GENGO + i][3] = NNumber.Parse(strTok[1]); // days since January 1: 92
|
|
5057
6083
|
this.MaxGengo++;
|
|
5058
6084
|
}
|
|
5059
6085
|
}
|
|
@@ -5062,12 +6088,24 @@ class UtilDateJpn {
|
|
|
5062
6088
|
}
|
|
5063
6089
|
}
|
|
5064
6090
|
|
|
6091
|
+
/// <summary>JPN: IME support
|
|
6092
|
+
/// Utility Class for Input Method Editor
|
|
6093
|
+
/// </summary>
|
|
6094
|
+
/// <author> Toshiro Nakayoshi (MSJ)
|
|
6095
|
+
/// </author>
|
|
5065
6096
|
class UtilImeJpn {
|
|
5066
6097
|
static IME_ZEN_HIRAGANA_ROMAN = 1;
|
|
5067
|
-
static IME_FORCE_OFF = 15;
|
|
5068
|
-
|
|
6098
|
+
static IME_FORCE_OFF = 15; // if (ImeMode property == 0 and (picture has K0 or PIC_S)) or
|
|
6099
|
+
// (attribute is not alpha, unicode, nor blob), set IME_FORCE_OFF.
|
|
6100
|
+
static IME_DISABLE = 10; // to completely disable IME (even not allowing to change the mode)
|
|
5069
6101
|
ImeAutoOff = false;
|
|
5070
6102
|
StrImeRead = null;
|
|
6103
|
+
/// <summary> check if the IME mode is within valid range
|
|
6104
|
+
/// </summary>
|
|
6105
|
+
/// <param name="imeMode">(IME mode in Magic)
|
|
6106
|
+
/// </param>
|
|
6107
|
+
/// <returns> bool
|
|
6108
|
+
/// </returns>
|
|
5071
6109
|
isValid(imeMode) {
|
|
5072
6110
|
return (0 <= imeMode && imeMode <= 9) || imeMode === 15 || imeMode === 10;
|
|
5073
6111
|
}
|
|
@@ -5075,15 +6113,25 @@ class UtilImeJpn {
|
|
|
5075
6113
|
}
|
|
5076
6114
|
}
|
|
5077
6115
|
|
|
6116
|
+
/// <summary> a helper class for the parsing of the XML</summary>
|
|
5078
6117
|
class XmlParser {
|
|
5079
6118
|
static endOfNameChar = [' ', '>'];
|
|
5080
6119
|
_currIndex = 0;
|
|
5081
6120
|
_xmLdata = "";
|
|
5082
|
-
_history = new List();
|
|
6121
|
+
_history = new List(); // In order to allow recursive parsing we save prev data
|
|
6122
|
+
/// <summary>
|
|
6123
|
+
///
|
|
6124
|
+
/// </summary>
|
|
6125
|
+
/// <param name="data"></param>
|
|
5083
6126
|
constructor(data = NString.Empty) {
|
|
5084
6127
|
this.setXMLdata(data);
|
|
5085
6128
|
this.setCurrIndex(0);
|
|
5086
6129
|
}
|
|
6130
|
+
/// <summary> parse a string according to a set of delimiters and return the result in a vector</summary>
|
|
6131
|
+
/// <param name="str">the String which need be parted </param>
|
|
6132
|
+
/// <param name="delimiter">the delimiter which part different parts of str </param>
|
|
6133
|
+
/// <param name="isMagicXML">is needed tokenizer working on Magic XML, so the "=" sign will be delited in the end of every first token </param>
|
|
6134
|
+
/// <returns> tmpVector dynamically array, which consist tokens in every element, every token is String </returns>
|
|
5087
6135
|
static getTokens(str, delimiter, isMagicXML = true) {
|
|
5088
6136
|
let tokensVec = new List();
|
|
5089
6137
|
let token = null;
|
|
@@ -5092,17 +6140,22 @@ class XmlParser {
|
|
|
5092
6140
|
}
|
|
5093
6141
|
let strTok = str.split(delimiter.charAt(0));
|
|
5094
6142
|
for (let i = 0; i < strTok.length; i = i + 1) {
|
|
6143
|
+
// Split in C# creates a last empty string token if the source string ends with
|
|
6144
|
+
// the delimiter or if the string is empty (as opposed to Java that will ignore it)
|
|
6145
|
+
// therefore we have to break this loop if such case occurs.
|
|
5095
6146
|
if (isMagicXML && i === strTok.length - 1 && strTok.length % 2 === 1) {
|
|
5096
6147
|
break;
|
|
5097
6148
|
}
|
|
5098
6149
|
token = strTok[i];
|
|
5099
6150
|
if (isMagicXML) {
|
|
6151
|
+
// the 1st token in the pair comes with "=", remove it.
|
|
5100
6152
|
if (i % 2 === 0) {
|
|
5101
6153
|
token = token.trim();
|
|
5102
6154
|
if (token.endsWith("=")) {
|
|
5103
6155
|
token = token.substr(0, token.length - 1);
|
|
5104
6156
|
}
|
|
5105
6157
|
}
|
|
6158
|
+
// 2nd token in the pair can be an empty string, in that case set it to " ".
|
|
5106
6159
|
else if (token === "")
|
|
5107
6160
|
token = " ";
|
|
5108
6161
|
}
|
|
@@ -5112,6 +6165,11 @@ class XmlParser {
|
|
|
5112
6165
|
}
|
|
5113
6166
|
return tokensVec;
|
|
5114
6167
|
}
|
|
6168
|
+
/// <summary>unscape from:
|
|
6169
|
+
/// {"&",\\, \q, \o, \l, \g, \e, \\r, \\n}, to:
|
|
6170
|
+
/// {"&", \, ", ', <, >, =, \r, \n}
|
|
6171
|
+
/// <param name="str">String to be converted</param>
|
|
6172
|
+
/// <returns>unescaped string</returns>
|
|
5115
6173
|
static unescape(str) {
|
|
5116
6174
|
let unescapedString = new StringBuilder(str.length);
|
|
5117
6175
|
for (let i = 0; i < str.length; i++) {
|
|
@@ -5148,6 +6206,11 @@ class XmlParser {
|
|
|
5148
6206
|
}
|
|
5149
6207
|
return (unescapedString.ToString());
|
|
5150
6208
|
}
|
|
6209
|
+
/// <summary>escape from:
|
|
6210
|
+
/// {\, ", ', <, >, =, \r, \n}, to:
|
|
6211
|
+
/// {\\, \q, \0, \l, \g, \e, \\r, \\n}
|
|
6212
|
+
/// <param name="str">String to be converted</param>
|
|
6213
|
+
/// <returns>escaped string</returns>
|
|
5151
6214
|
static escape(str) {
|
|
5152
6215
|
let escapedString = new StringBuilder(str.length * 2);
|
|
5153
6216
|
for (let i = 0; i < str.length; i++) {
|
|
@@ -5183,15 +6246,23 @@ class XmlParser {
|
|
|
5183
6246
|
}
|
|
5184
6247
|
return (escapedString.ToString());
|
|
5185
6248
|
}
|
|
6249
|
+
/// <summary>
|
|
6250
|
+
/// here we only need to take care of "&" so that Sax parser will be able to handle url
|
|
6251
|
+
/// </summary>
|
|
6252
|
+
/// <param name="str"></param>
|
|
6253
|
+
/// <returns></returns>
|
|
5186
6254
|
static escapeUrl(str) {
|
|
5187
6255
|
return NString.Replace(str, "&", "&");
|
|
5188
6256
|
}
|
|
6257
|
+
/// <summary>get next tag name from current index in XML string</summary>
|
|
6258
|
+
/// <returns> next tag name </returns>
|
|
5189
6259
|
getNextTag() {
|
|
5190
6260
|
if (this._xmLdata.length - this._currIndex <= 1) {
|
|
5191
|
-
return null;
|
|
6261
|
+
return null; // end of XML string
|
|
5192
6262
|
}
|
|
5193
6263
|
for (let tmpIndx = this._currIndex + 1; tmpIndx < this._xmLdata.length; tmpIndx++) {
|
|
5194
6264
|
let tmpChar = this._xmLdata[tmpIndx];
|
|
6265
|
+
// a letter starts an element and ends with " ". "/" starts an element closing and ends with '>'.
|
|
5195
6266
|
if (NChar.IsLetter(tmpChar) || tmpChar === '/') {
|
|
5196
6267
|
let endOfTag = NString.IndexOfAny(this._xmLdata, XmlParser.endOfNameChar, tmpIndx, this._xmLdata.length - tmpIndx);
|
|
5197
6268
|
if (endOfTag === -1)
|
|
@@ -5202,25 +6273,34 @@ class XmlParser {
|
|
|
5202
6273
|
}
|
|
5203
6274
|
return null;
|
|
5204
6275
|
}
|
|
6276
|
+
/// <summary>Substring of XMLstring</summary>
|
|
6277
|
+
/// <returns> substring of XML string -from currIndex to endContext </returns>
|
|
5205
6278
|
getXMLsubstring(endContext) {
|
|
5206
6279
|
return this._xmLdata.substr(this._currIndex, endContext - this._currIndex);
|
|
5207
6280
|
}
|
|
6281
|
+
/// <summary>get current element value</summary>
|
|
6282
|
+
/// <returns> element's value </returns>
|
|
5208
6283
|
GetCurrentElementValue() {
|
|
5209
6284
|
this.setCurrIndex2EndOfTag();
|
|
5210
6285
|
let endContext = this.getXMLdata().indexOf(XMLConstants.TAG_OPEN, this.getCurrIndex());
|
|
6286
|
+
// read value of xml element
|
|
5211
6287
|
let value = this.getXMLsubstring(endContext);
|
|
5212
6288
|
this.setCurrIndex2EndOfTag();
|
|
5213
6289
|
return value;
|
|
5214
6290
|
}
|
|
6291
|
+
/// <summary>set current index (on parsing time) to the end of current tag</summary>
|
|
5215
6292
|
setCurrIndex2EndOfTag() {
|
|
5216
6293
|
this._currIndex = this._xmLdata.indexOf(XMLConstants.TAG_CLOSE, this._currIndex) + 1;
|
|
5217
6294
|
}
|
|
6295
|
+
/// <summary>get int from string at parsing time</summary>
|
|
5218
6296
|
static getInt(valueStr) {
|
|
5219
6297
|
return NNumber.Parse(valueStr.trim());
|
|
5220
6298
|
}
|
|
6299
|
+
/// <summary>get boolean from string at parsing time</summary>
|
|
5221
6300
|
static getBoolean(valueStr) {
|
|
5222
6301
|
return valueStr[0] === '1';
|
|
5223
6302
|
}
|
|
6303
|
+
/// <summary>get/set functions 4 XMLstring & currIndex, for parser</summary>
|
|
5224
6304
|
getCurrIndex() {
|
|
5225
6305
|
return this._currIndex;
|
|
5226
6306
|
}
|
|
@@ -5241,46 +6321,81 @@ class XmlParser {
|
|
|
5241
6321
|
this.setCurrIndex(0);
|
|
5242
6322
|
}
|
|
5243
6323
|
}
|
|
6324
|
+
/// <summary>
|
|
6325
|
+
/// prepare the parser to read from the newXmlString
|
|
6326
|
+
/// </summary>
|
|
6327
|
+
/// <param name="newXmlString"></param>
|
|
5244
6328
|
PrepareFormReadString(newXmlString) {
|
|
5245
6329
|
this.setXMLdata(newXmlString);
|
|
5246
6330
|
this.setCurrIndex(0);
|
|
5247
6331
|
}
|
|
6332
|
+
/// <summary> push the current parsing information into the history stack</summary>
|
|
5248
6333
|
push() {
|
|
5249
6334
|
this._history.push(this._currIndex);
|
|
5250
6335
|
this._history.push(this._xmLdata);
|
|
5251
6336
|
}
|
|
6337
|
+
/// <summary> restore the previous parsing information from the history stack</summary>
|
|
5252
6338
|
pop() {
|
|
5253
6339
|
let count = this._history.length;
|
|
5254
6340
|
this._xmLdata = this._history.get_Item(count - 1);
|
|
5255
6341
|
this._currIndex = this._history.get_Item(count - 2);
|
|
5256
6342
|
this._history.SetSize(count - 2);
|
|
5257
6343
|
}
|
|
6344
|
+
/// <summary>gets a table cache xml and set the xmlparser data and index accordingly</summary>
|
|
5258
6345
|
loadTableCacheData(data) {
|
|
5259
6346
|
this.setXMLdata(data);
|
|
5260
6347
|
this.setCurrIndex(0);
|
|
5261
6348
|
}
|
|
6349
|
+
/// <summary>
|
|
6350
|
+
/// Reads the XML from the element at the current position until the end of
|
|
6351
|
+
/// the element, returning the contents as a string. This allows deferring the
|
|
6352
|
+
/// processing of an element until the time is right to do so.<br/>
|
|
6353
|
+
/// The returned string contains the element tag itself. For example:<br/>
|
|
6354
|
+
/// - Assuming that the current element is 'element1', with 2 'innerElement' elements, the
|
|
6355
|
+
/// resulting string will look like this:<br/>
|
|
6356
|
+
/// <element1>
|
|
6357
|
+
/// <innerelement/>
|
|
6358
|
+
/// <innerelement/>
|
|
6359
|
+
/// </element1>
|
|
6360
|
+
///
|
|
6361
|
+
/// This makes the result valid for processing by this XML parser.
|
|
6362
|
+
/// </summary>
|
|
6363
|
+
/// <returns></returns>
|
|
5262
6364
|
ReadToEndOfCurrentElement() {
|
|
6365
|
+
// Get the current tag according to the value of _currIndex.
|
|
5263
6366
|
let currentTag = this.getNextTag();
|
|
5264
6367
|
let currentTagIndex = this._xmLdata.indexOf(XMLConstants.TAG_OPEN + currentTag, this.getCurrIndex());
|
|
6368
|
+
// Find the end of the element's block in the XML.
|
|
6369
|
+
// find next open tag
|
|
5265
6370
|
let nextOpenTagIndex = this._xmLdata.indexOf(XMLConstants.TAG_OPEN, currentTagIndex + 1);
|
|
5266
6371
|
if (nextOpenTagIndex === -1)
|
|
5267
6372
|
nextOpenTagIndex = this._xmLdata.length;
|
|
6373
|
+
// find a close tag BEFORE the next open tag
|
|
5268
6374
|
let elementEndIndex = NString.IndexOf(this._xmLdata, XMLConstants.TAG_TERM, this.getCurrIndex(), nextOpenTagIndex - this.getCurrIndex());
|
|
5269
6375
|
if (elementEndIndex === -1)
|
|
6376
|
+
// close tag was not found in range - we have inner elements, look for the full close tag
|
|
5270
6377
|
elementEndIndex = this._xmLdata.indexOf("/" + currentTag, this.getCurrIndex()) + currentTag.length + XMLConstants.TAG_TERM.length;
|
|
5271
6378
|
else
|
|
5272
6379
|
elementEndIndex = elementEndIndex + XMLConstants.TAG_TERM.length;
|
|
6380
|
+
// Copy the element data so it can be returned.
|
|
5273
6381
|
let elementBlock = this.getXMLsubstring(elementEndIndex);
|
|
6382
|
+
// Move the parser to the end of the element block.
|
|
5274
6383
|
this.setCurrIndex(elementEndIndex);
|
|
5275
6384
|
return elementBlock;
|
|
5276
6385
|
}
|
|
5277
6386
|
ReadContentOfCurrentElement() {
|
|
6387
|
+
// Get the current tag according to the value of _currIndex.
|
|
5278
6388
|
let currentTag = this.getNextTag();
|
|
6389
|
+
// Find the end of the element's block in the XML.
|
|
5279
6390
|
let elementEndIndex = this._xmLdata.indexOf("</" + currentTag + ">", this.getCurrIndex());
|
|
5280
6391
|
if (elementEndIndex === -1)
|
|
6392
|
+
// Can't find the end of the current element - either XML is faulty or the element is empty.
|
|
5281
6393
|
return NString.Empty;
|
|
6394
|
+
// Move to the end of the opening tag
|
|
5282
6395
|
this.setCurrIndex2EndOfTag();
|
|
6396
|
+
// Copy the content of the element (from the end of the opening tag to the beginning of the closing tag).
|
|
5283
6397
|
let elementBlock = this.getXMLsubstring(elementEndIndex);
|
|
6398
|
+
// Move the parser to the end of the element block.
|
|
5284
6399
|
this.setCurrIndex(elementEndIndex);
|
|
5285
6400
|
this.setCurrIndex2EndOfTag();
|
|
5286
6401
|
return elementBlock;
|
|
@@ -5291,9 +6406,29 @@ class XmlParser {
|
|
|
5291
6406
|
}
|
|
5292
6407
|
return this.ToString_1(headCharCount, tailCharCount);
|
|
5293
6408
|
}
|
|
6409
|
+
/// <summary>
|
|
6410
|
+
/// Generates a string that visualizes the XML parser state (e.g. for debug watch list.)<br/>
|
|
6411
|
+
/// The method will show the XML data, trimming it to 20 characters before the
|
|
6412
|
+
/// current position (_currIndex) and up to 50 characters after the current position.
|
|
6413
|
+
/// The current position itself will be marked with a marker that looks like:
|
|
6414
|
+
/// |-{current index}-| <br/>
|
|
6415
|
+
/// The marker will be placed immediately before _xmlData[_currIndex].
|
|
6416
|
+
/// </summary>
|
|
6417
|
+
/// <returns></returns>
|
|
5294
6418
|
ToString_0() {
|
|
5295
6419
|
return this.toString(20, 50);
|
|
5296
6420
|
}
|
|
6421
|
+
/// <summary>
|
|
6422
|
+
/// Generates a string that visualizes the XML parser state (e.g. for debug watch list.)<br/>
|
|
6423
|
+
/// The method will show the XML data, trimming it to headCharCount characters before the
|
|
6424
|
+
/// current position (_currIndex) and up to tailCharCount characters after the current position.
|
|
6425
|
+
/// The current position itself will be marked with a marker that looks like:
|
|
6426
|
+
/// |-{current index}-| <br/>
|
|
6427
|
+
/// The marker will be placed immediately before _xmlData[_currIndex].
|
|
6428
|
+
/// </summary>
|
|
6429
|
+
/// <param name="headCharCount">Number of characters to show before the current position marker.</param>
|
|
6430
|
+
/// <param name="tailCharCount">Number of characters to show after the current position marker.</param>
|
|
6431
|
+
/// <returns></returns>
|
|
5297
6432
|
ToString_1(headCharCount, tailCharCount) {
|
|
5298
6433
|
let markerPosition = Math.min(this._currIndex, this._xmLdata.length);
|
|
5299
6434
|
let segmentStartIndex = Math.max(0, markerPosition - headCharCount);
|
|
@@ -5320,5 +6455,13 @@ class XmlParser {
|
|
|
5320
6455
|
}
|
|
5321
6456
|
}
|
|
5322
6457
|
|
|
6458
|
+
/**
|
|
6459
|
+
* @file Automatically generated by barrelsby.
|
|
6460
|
+
*/
|
|
6461
|
+
|
|
6462
|
+
/**
|
|
6463
|
+
* Generated bundle index. Do not edit.
|
|
6464
|
+
*/
|
|
6465
|
+
|
|
5323
6466
|
export { APGDisplayMode, APGFormSize, APGInvokedFrom, APGMode, APGOption, APGType, Access, AlignmentTypeHori, AlignmentTypeVert, AllowedDirectionType, Area, AutoFit, Axis, Base64, BindingLevel, BlobContent, BlockTypes, BorderType, BottomPositionInterval, BoxDir, BrkLevel, BrkScope, BrkType, CacheStrategy, CallComOption, CallOperationMode, CallOsShow, CallUDPType, CallUdpConvention, CallWsStyle, CallbackType, CharacterSet, CheckExist, CheckboxMainStyle, ChoiceControlStyle, ChoiceUtils, ColumnUpdateStyle, CompTypes, ComponentItemType, Constants, ControlStyle, CtrlButtonType, CtrlButtonTypeGui, CtrlHotspotType, CtrlImageStyle, CtrlLineDirection, CtrlLineType, CtrlOleDisplayType, CtrlOleStoreType, CtrlTextType, DBHCache, DBHRowIdentifier, DataTranslation, DataViewHeaderType, DataViewOperationType, DataViewOutputType, DatabaseDataType, DatabaseDefinitionType, DatabaseFilters, DatabaseOperations, DataviewType, DateTimeUtils, DateUtil, DbDelUpdMode, DbOpen, DbShare, DbhKeyDirection, DbhKeyIndexType, DbhKeyMode, DbhKeyRangeMode, DbhSegmentDirection, DefaultMsgDetails, DisplayTextType, DitAttribute, DitType, DriverDB, DspInterface, EndMode, EngineDirect, EnterAnimation, ErrStrategy, ErrorClassific, ExeState, ExecOn, ExitAnimation, ExportType, FieldComAlloc, FieldComType, FieldViewModelType, FldStorage, FldStyle, FlowDirection, FlwMode, ForceExit, FormDelimiter, FormExpandType, FormOperationType, FormPage, FrameLayoutTypes, GradientStyle, HTML_2_STR, HelpCommand, HelpType, HtmlAlignmentType, HttpStatusCode, ImageEffects, InitialMode, InternalInterface, ItemMasks, JSON_Utils, KeyMode, KeyboardReturnKeys, KeyboardTypes, LDir, LineDirection, LineManipulationType, ListboxSelectionMode, LnkEval_Cond, LnkMode, LoadedValues, LockingStrategy, LogType, Logger, Logger_LogLevels, Logger_MessageDirection, LogicHeaderAction, LogicHeaderType, LogicLevel, LogicOperationType, LogicUnit, MagicProperties, MediaAccess, MediaFormat, MediaOrientation, MediaType, MgControlType, MgModelType, Misc, ModelAttGuiFrame, ModelAttMerge, ModelAttRichClientFrameSet, ModelAttrBrowser, ModelAttrField, ModelAttrFramesetForm, ModelAttrGui0, ModelAttrGui1, ModelAttrHelp, ModelAttrRichClient, ModelAttrText, ModelClass, MsgInterface, NotifyCollectionChangedAction, NullArithmetic, OSEnvironment, OSType, OpenEditDialog, Opr, Order, OrientationLock, PICInterface, PaperSize, PaperSizePdfDisabled, PaperSizePdfEnabled, PositionUsage, PrgExecPlace, Priority, Queue, RaiseAt, Randomizer, RangeMode, RbAppearance, Recursion, RemarkType, RequestInfo, Resident, RowType, Rtf, Rtf_ACTN, Rtf_ErrorRtf, Rtf_IDEST, Rtf_IPFN, Rtf_IPROP, Rtf_KWD, Rtf_PROP, Rtf_PROPTYPE, Rtf_RDS, Rtf_RIS, Rtf_RtfChar, Rtf_SYMBOL, SEQ_2_HTML, SEQ_2_STR, ScrollBarThumbType, SelprgMode, SideType, SliderType, SourceContextType, SplitPrimaryDisplay, SplitWindowType, StartupMode, Storage, StorageAttribute, StorageAttributeCheck, StorageAttributeType, StrUtil, SubformType, SyncExecutionHelper, TabControlTabsWidth, TabbingCycleType, TabbingOrderType, TableBehaviour, TableType, TaskFlow, TransBegin, TransMode, TriggerType, TrueFalseValues, UndoRedoAction, UniqueTskSort, UpdateMode, UseSQLCursor, UtilDateJpn, UtilImeJpn, UtilStrByteMode, ValType, VeeDiffUpdate, VeeMode, VeePartOfDataview, VerifyButtons, VerifyDisplay, VerifyImage, VerifyMode, ViewRefreshMode, ViewSelectType, WinCptn, WinHtmlType, WinUom, WindowPosition, WindowType, XMLConstants, XmlParser, YesNoValues };
|
|
5324
6467
|
//# sourceMappingURL=magic-xpa-utils.mjs.map
|