1 |
// Upgraded to Delphi 2009: Sebastian Zierer
|
2 |
|
3 |
(* ***** BEGIN LICENSE BLOCK *****
|
4 |
* Version: MPL 1.1
|
5 |
*
|
6 |
* The contents of this file are subject to the Mozilla Public License Version
|
7 |
* 1.1 (the "License"); you may not use this file except in compliance with
|
8 |
* the License. You may obtain a copy of the License at
|
9 |
* http://www.mozilla.org/MPL/
|
10 |
*
|
11 |
* Software distributed under the License is distributed on an "AS IS" basis,
|
12 |
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
|
13 |
* for the specific language governing rights and limitations under the
|
14 |
* License.
|
15 |
*
|
16 |
* The Original Code is TurboPower SysTools
|
17 |
*
|
18 |
* The Initial Developer of the Original Code is
|
19 |
* TurboPower Software
|
20 |
*
|
21 |
* Portions created by the Initial Developer are Copyright (C) 1996-2002
|
22 |
* the Initial Developer. All Rights Reserved.
|
23 |
*
|
24 |
* Contributor(s):
|
25 |
*
|
26 |
* ***** END LICENSE BLOCK ***** *)
|
27 |
|
28 |
{*********************************************************}
|
29 |
{* SysTools: StDateSt.pas 4.04 *}
|
30 |
{*********************************************************}
|
31 |
{* SysTools: Date and time string manipulation *}
|
32 |
{*********************************************************}
|
33 |
|
34 |
{$I StDefine.inc}
|
35 |
|
36 |
unit StDateSt;
|
37 |
|
38 |
interface
|
39 |
|
40 |
uses
|
41 |
Windows, SysUtils,
|
42 |
StStrS,
|
43 |
StStrL,
|
44 |
StConst,
|
45 |
StBase,
|
46 |
StUtils,
|
47 |
StDate;
|
48 |
|
49 |
const
|
50 |
{the following characters are meaningful in date Picture strings}
|
51 |
MonthOnly = 'm'; {Formatting character for a date string picture mask}
|
52 |
DayOnly = 'd'; {Formatting character for a date string picture mask}
|
53 |
YearOnly = 'y'; {Formatting character for a date string picture mask}
|
54 |
MonthOnlyU = 'M'; {Formatting character for a date string picture mask.
|
55 |
Uppercase means pad with ' ' rather than '0'}
|
56 |
DayOnlyU = 'D'; {Formatting character for a date string picture mask.
|
57 |
Uppercase means pad with ' ' rather then '0'}
|
58 |
DateSlash = '/'; {Formatting character for a date string picture mask}
|
59 |
|
60 |
{'n'/'N' may be used in place of 'm'/'M' when the name of the month is
|
61 |
desired instead of its number. E.g., 'dd/nnn/yyyy' -\> '01-Jan-1980'.
|
62 |
'dd/NNN/yyyy' -\> '01-JAN-1980' (if SlashChar = '-'). The abbreviation used
|
63 |
is based on the width of the subfield (3 in the example) and the current
|
64 |
contents of the MonthString array.}
|
65 |
NameOnly = 'n'; {Formatting character for a date string picture mask}
|
66 |
NameOnlyU = 'N'; {Formatting character for a date string picture mask.
|
67 |
Uppercase causes the output to be in uppercase}
|
68 |
|
69 |
{'w'/'W' may be used to include the day of the week in a date string. E.g.,
|
70 |
'www dd nnn yyyy' -\> 'Mon 01 Jan 1989'. The abbreviation used is based on
|
71 |
the width of the subfield (3 in the example) and the current contents of the
|
72 |
DayString array. Note that TurboPower Entry Fields will not allow the user to
|
73 |
enter text into a subfield containing 'w' or 'W'. The day of the week will be
|
74 |
supplied automatically when a valid date is entered.}
|
75 |
WeekDayOnly = 'w'; {Formatting character for a date string picture mask}
|
76 |
WeekDayOnlyU = 'W'; {Formatting character for a date string picture mask.
|
77 |
Uppercase causes the output to be in uppercase}
|
78 |
|
79 |
LongDateSub1 = 'f'; {Mask character used strictly for dealing with Window's
|
80 |
long date format}
|
81 |
LongDateSub2 = 'g'; {Mask character used strictly for dealing with Window's
|
82 |
long date format}
|
83 |
LongDateSub3 = 'h'; {Mask character used strictly for dealing with Window's
|
84 |
long date format}
|
85 |
|
86 |
HourOnly = 'h'; {Formatting character for a time string picture mask}
|
87 |
MinOnly = 'm'; {Formatting character for a time string picture mask}
|
88 |
SecOnly = 's'; {Formatting character for a time string picture mask}
|
89 |
{if uppercase letters are used, numbers are padded with ' ' rather than '0'}
|
90 |
HourOnlyU = 'H'; {Formatting character for a time string picture mask.
|
91 |
Uppercase means pad with ' ' rather than '0'}
|
92 |
MinOnlyU = 'M'; {Formatting character for a time string picture mask.
|
93 |
Uppercase means pad with ' ' rather than '0'}
|
94 |
SecOnlyU = 'S'; {Formatting character for a time string picture mask.
|
95 |
Uppercase means pad with ' ' rather than '0'}
|
96 |
{'hh:mm:ss tt' -\> '12:00:00 pm', 'hh:mmt' -\> '12:00p'}
|
97 |
TimeOnly = 't'; {Formatting character for a time string picture mask.
|
98 |
This generates 'AM' or 'PM'}
|
99 |
TimeColon = ':'; {Formatting character for a time string picture mask}
|
100 |
|
101 |
|
102 |
{-------julian date routines---------------}
|
103 |
|
104 |
function DateStringHMStoAstJD(const Picture, DS : string; {!!.02}
|
105 |
H,M,S,Epoch : integer) : Double;
|
106 |
{-Returns the Astronomical Julian Date using a Date String,
|
107 |
Hours, Minutes, Seconds}
|
108 |
|
109 |
function MonthToString(const Month : Integer) : string;
|
110 |
{-Return the month as a string}
|
111 |
|
112 |
{-------date string routines---------------}
|
113 |
|
114 |
function DateStringToStDate(const Picture, S : string; Epoch : Integer) : TStDate;
|
115 |
{-Convert a string to a Julian date}
|
116 |
|
117 |
function DateStringToDMY(const Picture, S : string;
|
118 |
Epoch : Integer;
|
119 |
var D, M, Y : Integer) : Boolean;
|
120 |
{-Extract day, month, and year from a date string}
|
121 |
|
122 |
function StDateToDateString(const Picture : string; const Julian : TStDate;
|
123 |
Pack : Boolean) : string;
|
124 |
{-Convert a Julian date to a string}
|
125 |
|
126 |
function DayOfWeekToString(const WeekDay : TStDayType) : string;
|
127 |
{-Return the day of the week specified by WeekDay as a string in Dest.}
|
128 |
|
129 |
function DMYtoDateString(const Picture : string;
|
130 |
Day, Month, Year, Epoch : Integer;
|
131 |
Pack : Boolean) : string;
|
132 |
{-Merge the month, day, and year into the picture}
|
133 |
|
134 |
function CurrentDateString(const Picture : string; Pack : Boolean) : string;
|
135 |
{-Return today's date as a string}
|
136 |
|
137 |
{-------time routines---------------}
|
138 |
|
139 |
function CurrentTimeString(const Picture : string;
|
140 |
Pack : Boolean) : string;
|
141 |
{-Return the current time as a string of the specified form}
|
142 |
|
143 |
function TimeStringToHMS(const Picture, St : string;
|
144 |
var H, M, S : Integer) : Boolean;
|
145 |
{-Extract hours, minutes, seconds from a time string}
|
146 |
|
147 |
function TimeStringToStTime(const Picture, S : string) : TStTime;
|
148 |
{-Convert a time string to a time variable}
|
149 |
|
150 |
function StTimeToAmPmString(const Picture : string;
|
151 |
const T : TStTime; Pack : Boolean) : string;
|
152 |
{-Convert a time variable to a time string in am/pm format}
|
153 |
|
154 |
function StTimeToTimeString(const Picture : string; const T : TStTime;
|
155 |
Pack : Boolean) : string;
|
156 |
{-Convert a time variable to a time string}
|
157 |
|
158 |
|
159 |
{-------- routines for international date/time strings ---------}
|
160 |
|
161 |
function DateStringIsBlank(const Picture, S : string) : Boolean;
|
162 |
{-Return True if the month, day, and year in S are all blank}
|
163 |
|
164 |
function InternationalDate(ForceCentury : Boolean) : string;
|
165 |
{-Return a picture mask for a short date string, based on Windows' international
|
166 |
information}
|
167 |
|
168 |
function InternationalLongDate(ShortNames : Boolean;
|
169 |
ExcludeDOW : Boolean) : string;
|
170 |
{-Return a picture mask for a date string, based on Windows' international
|
171 |
information}
|
172 |
|
173 |
function InternationalTime(ShowSeconds : Boolean) : string;
|
174 |
{-Return a picture mask for a time string, based on Windows' international
|
175 |
information}
|
176 |
|
177 |
procedure ResetInternationalInfo;
|
178 |
{-Update internal info to match Windows' international info}
|
179 |
|
180 |
|
181 |
implementation
|
182 |
|
183 |
const
|
184 |
First2Months = 59; {1600 was a leap year}
|
185 |
FirstDayOfWeek = Saturday; {01/01/1600 was a Saturday}
|
186 |
DateLen = 40; {maximum length of Picture strings}
|
187 |
MaxMonthName = 15;
|
188 |
MaxDayName = 15;
|
189 |
|
190 |
//type
|
191 |
{ DateString = string[DateLen];}
|
192 |
// SString = string[255];
|
193 |
|
194 |
var
|
195 |
wLongDate : string;//[40];
|
196 |
wldSub1 : string[6]; //SZ: careful if converting to string; some code depends on sizeof (search for [*] around line 1021)
|
197 |
wldSub2 : string[6];
|
198 |
wldSub3 : string[6];
|
199 |
wShortDate : string;//[31];
|
200 |
w1159 : string[7];
|
201 |
w2359 : string[7];
|
202 |
wSlashChar : Char;
|
203 |
wColonChar : Char;
|
204 |
wTLZero : Boolean;
|
205 |
w12Hour : Boolean;
|
206 |
DefaultYear : Integer; {default year--used by DateStringToDMY}
|
207 |
DefaultMonth : ShortInt; {default month}
|
208 |
|
209 |
procedure ExtractFromPicture(const Picture, S : string; Ch : Char; {!!.02}
|
210 |
var I : Integer; Blank, Default : Integer); forward;
|
211 |
|
212 |
procedure AppendChar(var S : String; Ch : Char);
|
213 |
begin
|
214 |
SetLength(S,Succ(Length(S)));
|
215 |
S[Length(S)] := Ch;
|
216 |
end;
|
217 |
|
218 |
function DayOfWeekToString(const WeekDay : TStDayType) : string;
|
219 |
{-Return the day of the week specified by WeekDay as a string in Dest.
|
220 |
Will honor international names}
|
221 |
begin
|
222 |
Result := {$IFDEF DELPHIXE2}FormatSettings.{$ENDIF}LongDayNames[Ord(WeekDay)+1];
|
223 |
end;
|
224 |
|
225 |
function MonthToString(const Month : Integer) : string;
|
226 |
{-Return the month as a string. Will honor international names}
|
227 |
begin
|
228 |
if (Month >= 1) and (Month <= 12) then
|
229 |
Result := {$IFDEF DELPHIXE2}FormatSettings.{$ENDIF}LongMonthNames[Month]
|
230 |
else
|
231 |
Result := '';
|
232 |
end;
|
233 |
|
234 |
function AstJulianDatePrim(Year,Month,Date : Integer) : Double;
|
235 |
var
|
236 |
A, B : integer;
|
237 |
begin
|
238 |
if Month <= 2 then {!!.01}
|
239 |
begin
|
240 |
Dec(Year);
|
241 |
Inc(Month,12);
|
242 |
end;
|
243 |
A := Trunc(Year/100);
|
244 |
B := 2 - A + Trunc(A/4);
|
245 |
|
246 |
Result := Trunc(365.25 * (Year+4716))
|
247 |
+ Trunc(30.6001 * (Month+1))
|
248 |
+ Date + B - 1524.5;
|
249 |
end;
|
250 |
|
251 |
function DateStringHMSToAstJD(const Picture, DS : string; {!!.02}
|
252 |
H,M,S,Epoch : Integer) : Double;
|
253 |
{-Returns the Astronomical Julian Date using a Date String,
|
254 |
Hours, Minutes, Seconds}
|
255 |
var
|
256 |
Date, Month, Year : Integer;
|
257 |
begin
|
258 |
ExtractFromPicture(Picture, DS, NameOnly, Month, -1, 0);
|
259 |
if Month = 0 then
|
260 |
ExtractFromPicture(Picture, DS, MonthOnly, Month, -1, DefaultMonth);
|
261 |
ExtractFromPicture(Picture, DS, DayOnly, Date, -1, 1);
|
262 |
ExtractFromPicture(Picture, DS, YearOnly, Year, -1, DefaultYear);
|
263 |
|
264 |
Year := ResolveEpoch(Year, Epoch);
|
265 |
Result := AstJulianDatePrim(Year,Month,Date)
|
266 |
+ H/HoursInDay + M/MinutesInDay + S/SecondsInDay;
|
267 |
end;
|
268 |
|
269 |
function MonthStringToMonth(const MSt : string; Width : Byte) : Byte;{!!.02}
|
270 |
{-Convert the month name in MSt to a month (1..12)}
|
271 |
var
|
272 |
S : String;
|
273 |
T : String;
|
274 |
Len : Byte;
|
275 |
I : Word;
|
276 |
begin
|
277 |
S := UpperCase(MSt);
|
278 |
Len := Length(S);
|
279 |
// SetLength(S,Width);
|
280 |
// if Width > Len then
|
281 |
// FillChar(S[Len+1], Length(S)-Len, ' ');
|
282 |
S := S + StringOfChar(' ', Width - Len);
|
283 |
|
284 |
for I := 1 to 12 do begin
|
285 |
T := UpperCase({$IFDEF DELPHIXE2}FormatSettings.{$ENDIF}LongMonthNames[I]);
|
286 |
Len := Length(T);
|
287 |
// SetLength(T,Width);
|
288 |
// if Width > Len then
|
289 |
// FillChar(T[Len+1], Length(T)-Len, ' ');
|
290 |
T := T + StringOfChar(' ', Width - Len);
|
291 |
|
292 |
if S = T then begin
|
293 |
Result := I;
|
294 |
Exit;
|
295 |
end;
|
296 |
end;
|
297 |
Result := 0;
|
298 |
end;
|
299 |
|
300 |
procedure ExtractFromPicture(const Picture, S : string; Ch : Char; {!!.02}
|
301 |
var I : Integer; Blank, Default : Integer);
|
302 |
{-Extract the value of the subfield specified by Ch from S and return in
|
303 |
I. I will be set to -1 in case of an error, Blank if the subfield exists
|
304 |
in Picture but is empty, Default if the subfield doesn't exist in
|
305 |
Picture.}
|
306 |
var
|
307 |
PTmp : string;
|
308 |
C, posLCCh, posUCCh : Cardinal;
|
309 |
Code : Integer;
|
310 |
begin
|
311 |
{find the start of the subfield}
|
312 |
I := Default;
|
313 |
|
314 |
StrChPosL(Picture, Ch, posLCCh);
|
315 |
Ch := StBase.Upcase(Ch);
|
316 |
StrChPosL(Picture, Ch, posUCCh);
|
317 |
|
318 |
if (posLCCh < 1) or ((posUCCh > 0) and (posUCCh < posLCCh)) then
|
319 |
posLCCh := posUCCh;
|
320 |
if (posLCCh < 1) or (Length(S) <> Length(Picture)) then
|
321 |
Exit;
|
322 |
|
323 |
{extract the substring}
|
324 |
|
325 |
PTmp := '';
|
326 |
C := Length(Picture);
|
327 |
while (posLCCh <= C) and (StBase.Upcase(Picture[posLCCh]) = Ch) do begin
|
328 |
if S[posLCCh] <> ' ' then
|
329 |
AppendChar(PTmp,Char(S[posLCCh]));
|
330 |
Inc(posLCCh);
|
331 |
end;
|
332 |
|
333 |
if Length(PTmp) = 0 then
|
334 |
I := Blank
|
335 |
else if Ch = NameOnlyU then begin
|
336 |
I := MonthStringToMonth(PTmp, Length(PTmp));
|
337 |
if I = 0 then
|
338 |
I := -1;
|
339 |
end
|
340 |
else begin
|
341 |
{convert to a value}
|
342 |
Val(PTmp, I, Code);
|
343 |
if Code <> 0 then
|
344 |
I := -1;
|
345 |
end;
|
346 |
end;
|
347 |
|
348 |
function DateStringToDMY(const Picture, S : string;
|
349 |
Epoch : Integer;
|
350 |
var D, M, Y : Integer) : Boolean;
|
351 |
{-Extract day, month, and year from S, returning true if string is valid}
|
352 |
begin
|
353 |
ExtractFromPicture(Picture, S, NameOnly, M, -1, 0);
|
354 |
if M = 0 then
|
355 |
ExtractFromPicture(Picture, S, MonthOnly, M, -1, DefaultMonth);
|
356 |
ExtractFromPicture(Picture, S, DayOnly, D, -1, 1);
|
357 |
ExtractFromPicture(Picture, S, YearOnly, Y, -1, DefaultYear);
|
358 |
if ValidDate(D, M, Y, Epoch) then begin
|
359 |
Result := True;
|
360 |
Y := ResolveEpoch(Y, Epoch);
|
361 |
end else
|
362 |
Result := False;
|
363 |
end;
|
364 |
|
365 |
function DateStringIsBlank(const Picture, S : string) : Boolean;
|
366 |
{-Return True if the month, day, and year in S are all blank}
|
367 |
var
|
368 |
M, D, Y : Integer;
|
369 |
begin
|
370 |
ExtractFromPicture(Picture, S, NameOnly, M, -2, 0);
|
371 |
if M = 0 then
|
372 |
ExtractFromPicture(Picture, S, MonthOnly, M, -2, -2);
|
373 |
ExtractFromPicture(Picture, S, DayOnly, D, -2, -2);
|
374 |
ExtractFromPicture(Picture, S, YearOnly, Y, -2, -2);
|
375 |
Result := (M = -2) and (D = -2) and (Y = -2);
|
376 |
end;
|
377 |
|
378 |
|
379 |
function DateStringToStDate(const Picture, S : string; Epoch : Integer) : TStDate;
|
380 |
{-Convert S, a string of the form indicated by Picture, to a julian date.
|
381 |
Picture and S must be of equal lengths}
|
382 |
var
|
383 |
Month, Day, Year : Integer;
|
384 |
begin
|
385 |
{extract day, month, year from S}
|
386 |
if DateStringToDMY(Picture, S, Epoch, Day, Month, Year) then
|
387 |
{convert to julian date}
|
388 |
Result := DMYtoStDate(Day, Month, Year, Epoch)
|
389 |
else
|
390 |
Result := BadDate;
|
391 |
end;
|
392 |
|
393 |
function SubstCharSim(P : string; OC, NC : Char) : string;
|
394 |
var
|
395 |
step : integer;
|
396 |
begin
|
397 |
for step := 1 to Length(P) do
|
398 |
begin
|
399 |
if P[step] = OC then
|
400 |
P[step] := NC;
|
401 |
end;
|
402 |
Result := P;
|
403 |
end;
|
404 |
|
405 |
function SubstChar(Picture : string; OldCh, NewCh : Char) : string;
|
406 |
{-Replace all instances of OldCh in Picture with NewCh}
|
407 |
var
|
408 |
I : Integer;
|
409 |
UpCh : Char;
|
410 |
P : Cardinal;
|
411 |
begin
|
412 |
UpCh := StBase.Upcase(OldCh);
|
413 |
if (StrChPosL(Picture,OldCh,P)) or (StrChPosL(Picture,UpCh,P)) then
|
414 |
for I := 1 to Length(Picture) do
|
415 |
if StBase.Upcase(Picture[I]) = UpCh then
|
416 |
Picture[I] := NewCh;
|
417 |
Result := Picture;
|
418 |
end;
|
419 |
|
420 |
function PackResult(const Picture, S : string) : string; {!!.02}
|
421 |
{-Remove unnecessary blanks from S}
|
422 |
var
|
423 |
step : Integer;
|
424 |
begin
|
425 |
Result := '';
|
426 |
|
427 |
for step := 1 to Length(Picture) do
|
428 |
begin
|
429 |
case Picture[step] of
|
430 |
MonthOnlyU, DayOnlyU, NameOnly, NameOnlyU, WeekDayOnly,
|
431 |
WeekDayOnlyU, HourOnlyU, SecOnlyU :
|
432 |
if S[step] <> ' ' then
|
433 |
AppendChar(Result,S[Step]);
|
434 |
TimeOnly :
|
435 |
if S[step] <> ' ' then
|
436 |
AppendChar(Result,S[step]);
|
437 |
else
|
438 |
AppendChar(Result,S[step]);
|
439 |
end;
|
440 |
end;
|
441 |
end;
|
442 |
|
443 |
procedure MergeIntoPicture(var Picture : string; Ch : Char; I : Integer);
|
444 |
{-Merge I into location in Picture indicated by format character Ch}
|
445 |
var
|
446 |
Tmp : string;
|
447 |
C,
|
448 |
J, K, L : Cardinal;
|
449 |
UCh,
|
450 |
CPJ,
|
451 |
CTI : Char;
|
452 |
OK, Done: Boolean;
|
453 |
step : Cardinal;
|
454 |
begin
|
455 |
{find the start of the subfield}
|
456 |
OK := StrChPosL(Picture,Ch,J);
|
457 |
UCh := StBase.Upcase(Ch);
|
458 |
if (NOT OK) then
|
459 |
begin
|
460 |
if NOT (StrChPosL(Picture, UCh, J)) then
|
461 |
Exit;
|
462 |
end;
|
463 |
|
464 |
{find the end of the subfield}
|
465 |
K := J;
|
466 |
C := Length(Picture);
|
467 |
while (J <= C) and (StBase.Upcase(Picture[J]) = UCh) do
|
468 |
Inc(J);
|
469 |
Dec(J);
|
470 |
|
471 |
if (UCh = WeekDayOnlyU) or (UCh = NameOnlyU) then begin
|
472 |
if UCh = WeekDayOnlyU then
|
473 |
case I of
|
474 |
Ord(Sunday)..Ord(Saturday) :
|
475 |
Tmp := {$IFDEF DELPHIXE2}FormatSettings.{$ENDIF}LongDayNames[I+1];
|
476 |
else
|
477 |
Tmp := '';
|
478 |
end
|
479 |
else
|
480 |
case I of
|
481 |
1..12 :
|
482 |
Tmp := {$IFDEF DELPHIXE2}FormatSettings.{$ENDIF}LongMonthNames[I];
|
483 |
else
|
484 |
Tmp := '';
|
485 |
end;
|
486 |
K := Succ(J-K);
|
487 |
if K > Length(Tmp) then
|
488 |
for step := 1 to (K-Length(Tmp)) do
|
489 |
Tmp := Tmp + ' ';
|
490 |
Tmp := Copy(Tmp,1,K);
|
491 |
end else
|
492 |
{convert I to a string}
|
493 |
Str(I:DateLen, Tmp);
|
494 |
|
495 |
{now merge}
|
496 |
L := Length(Tmp);
|
497 |
Done := False;
|
498 |
CPJ := Picture[J];
|
499 |
|
500 |
while (stBase.Upcase(CPJ) = UCh) and not Done do
|
501 |
begin
|
502 |
CTI := Tmp[L];
|
503 |
if (UCh = NameOnlyU) or (UCh = WeekDayOnlyU) then
|
504 |
begin
|
505 |
case CPJ of
|
506 |
NameOnlyU, WeekDayOnlyU :
|
507 |
CTI := stBase.Upcase(CTI);
|
508 |
end;
|
509 |
end
|
510 |
else{change spaces to 0's if desired}
|
511 |
if (CPJ >= 'a') and (CTI = ' ') then
|
512 |
CTI := '0';
|
513 |
Picture[J] := CTI;
|
514 |
Done := (J = 1) or (L = 0);
|
515 |
if not Done then
|
516 |
begin
|
517 |
Dec(J);
|
518 |
Dec(L);
|
519 |
end;
|
520 |
CPJ := Picture[J];
|
521 |
end;
|
522 |
end;
|
523 |
|
524 |
|
525 |
procedure MergePictureSt(const Picture : string; var P : string; {!!.02}
|
526 |
MC : Char; const SP : string); {!!.02}
|
527 |
var
|
528 |
I, J : Cardinal;
|
529 |
L : Cardinal;
|
530 |
begin
|
531 |
if NOT (StrChPosL(Picture,MC,I)) then
|
532 |
Exit;
|
533 |
J := 1;
|
534 |
L := Length(SP);
|
535 |
while Picture[I] = MC do begin
|
536 |
{if J <= Length(SP) then}
|
537 |
if (L = 0) or (J > L) then
|
538 |
P[I] := ' '
|
539 |
else begin
|
540 |
P[I] := SP[J];
|
541 |
Inc(J);
|
542 |
end;
|
543 |
Inc(I);
|
544 |
end;
|
545 |
end;
|
546 |
|
547 |
|
548 |
function DMYtoDateString(const Picture : string; Day, Month, Year, Epoch : Integer;
|
549 |
Pack : Boolean) : string;
|
550 |
{-Merge the month, day, and year into the picture}
|
551 |
var
|
552 |
DOW : Integer;
|
553 |
|
554 |
begin
|
555 |
Result := Picture;
|
556 |
|
557 |
Year := ResolveEpoch(Year, Epoch);
|
558 |
|
559 |
DOW := Integer( DayOfWeekDMY(Day, Month, Year, 0) );
|
560 |
MergeIntoPicture(Result, MonthOnly, Month);
|
561 |
MergeIntoPicture(Result, DayOnly, Day);
|
562 |
MergeIntoPicture(Result, YearOnly, Year);
|
563 |
MergeIntoPicture(Result, NameOnly, Month);
|
564 |
MergeIntoPicture(Result, WeekDayOnly, DOW);
|
565 |
|
566 |
{map slashes}
|
567 |
Result := SubstChar(Result, DateSlash, wSlashChar);
|
568 |
|
569 |
MergePictureSt(Picture, Result, LongDateSub1, wldSub1);
|
570 |
MergePictureSt(Picture, Result, LongDateSub2, wldSub2);
|
571 |
MergePictureSt(Picture, Result, LongDateSub3, wldSub3);
|
572 |
|
573 |
if Pack then
|
574 |
Result:= PackResult(Picture, Result);
|
575 |
end;
|
576 |
|
577 |
function StDateToDateString(const Picture : string; const Julian : TStDate;
|
578 |
Pack : Boolean) : string;
|
579 |
{-Convert Julian to a string of the form indicated by Picture}
|
580 |
var
|
581 |
Month, Day, Year : Integer;
|
582 |
begin
|
583 |
Result := Picture;
|
584 |
if (Julian = BadDate) or (Julian > MaxDate) then begin {!!.04}
|
585 |
{map picture characters to spaces}
|
586 |
Result := SubstChar(Result, MonthOnly, ' ');
|
587 |
Result := SubstChar(Result, NameOnly, ' ');
|
588 |
Result := SubstChar(Result, DayOnly, ' ');
|
589 |
Result := SubstChar(Result, YearOnly, ' ');
|
590 |
Result := SubstChar(Result, WeekDayOnly, ' ');
|
591 |
|
592 |
MergePictureSt(Picture, Result, LongDateSub1, wldSub1);
|
593 |
MergePictureSt(Picture, Result, LongDateSub2, wldSub2);
|
594 |
MergePictureSt(Picture, Result, LongDateSub3, wldSub3);
|
595 |
|
596 |
{map slashes}
|
597 |
Result := SubstChar(Result, DateSlash, wSlashChar);
|
598 |
end
|
599 |
else begin
|
600 |
{convert Julian to day/month/year}
|
601 |
StDateToDMY(Julian, Day, Month, Year);
|
602 |
|
603 |
{merge the month, day, and year into the picture}
|
604 |
Result := DMYtoDateString(Picture, Day, Month, Year, 0, Pack);
|
605 |
end;
|
606 |
end;
|
607 |
|
608 |
function CurrentDateString(const Picture : string; Pack : Boolean) : string;
|
609 |
{-Returns today's date as a string of the specified form}
|
610 |
begin
|
611 |
Result := StDateToDateString(Picture, CurrentDate, Pack);
|
612 |
end;
|
613 |
|
614 |
function TimeStringToHMS(const Picture, St : string; var H, M, S : Integer) : Boolean;
|
615 |
{-Extract Hours, Minutes, Seconds from St, returning true if string is valid}
|
616 |
var
|
617 |
I,
|
618 |
J : Cardinal;
|
619 |
Tmp,
|
620 |
t1159,
|
621 |
t2359 : string;
|
622 |
begin
|
623 |
{extract hours, minutes, seconds from St}
|
624 |
ExtractFromPicture(Picture, St, HourOnly, H, -1, 0);
|
625 |
ExtractFromPicture(Picture, St, MinOnly, M, -1, 0);
|
626 |
ExtractFromPicture(Picture, St, SecOnly, S, -1, 0);
|
627 |
if (H = -1) or (M = -1) or (S = -1) then begin
|
628 |
Result := False;
|
629 |
Exit;
|
630 |
end;
|
631 |
|
632 |
{check for TimeOnly}
|
633 |
if (StrChPosL(Picture, TimeOnly, I)) and
|
634 |
(Length(w1159) > 0) and (Length(w2359) > 0) then begin
|
635 |
|
636 |
Tmp := '';
|
637 |
J := 1;
|
638 |
while (I <= Cardinal(Length(Picture))) and (Picture[I] = TimeOnly) do begin{!!.02}
|
639 |
// while (Picture[I] = TimeOnly) do begin
|
640 |
//SZ Inc(Tmp[0]);
|
641 |
//SZ Tmp[J] := St[I];
|
642 |
Tmp := Tmp + St[I];
|
643 |
Inc(J);
|
644 |
Inc(I);
|
645 |
end;
|
646 |
Tmp := TrimRight(Tmp);
|
647 |
|
648 |
t1159 := w1159;
|
649 |
t2359 := w2359;
|
650 |
if (Length(Tmp) = 0) then
|
651 |
H := -1
|
652 |
else if (UpperCase(Tmp) = UpperCase(t2359)) then begin
|
653 |
if (H < 12) then
|
654 |
Inc(H,12)
|
655 |
else if (H=0) or (H > 12) then
|
656 |
{force BadTime}
|
657 |
H := -1;
|
658 |
end
|
659 |
else if (UpperCase(Tmp) = UpperCase(t1159)) then begin
|
660 |
if H = 12 then
|
661 |
H := 0
|
662 |
else if (H = 0) or (H > 12) then
|
663 |
{force BadTime}
|
664 |
H := -1;
|
665 |
end
|
666 |
else
|
667 |
{force BadTime}
|
668 |
H := -1;
|
669 |
end;
|
670 |
Result := ValidTime(H, M, S);
|
671 |
end;
|
672 |
|
673 |
function TimeStringToStTime(const Picture, S : string) : TStTime;
|
674 |
{-Convert S, a string of the form indicated by Picture, to a Time variable}
|
675 |
var
|
676 |
Hours, Minutes, Seconds : Integer;
|
677 |
begin
|
678 |
if TimeStringToHMS(Picture, S, Hours, Minutes, Seconds) then
|
679 |
Result := HMStoStTime(Hours, Minutes, Seconds)
|
680 |
else
|
681 |
Result := BadTime;
|
682 |
end;
|
683 |
|
684 |
function TimeToTimeStringPrim(const Picture : string; T : TStTime; {!!.02}
|
685 |
Pack : Boolean;
|
686 |
const t1159, t2359 : string) : string; {!!.02}
|
687 |
{-Convert T to a string of the form indicated by Picture}
|
688 |
var
|
689 |
Hours,
|
690 |
Minutes,
|
691 |
Seconds : Byte;
|
692 |
L, I,
|
693 |
TPos : Cardinal;
|
694 |
P : string;
|
695 |
OK : Boolean;
|
696 |
C : string;//[1];
|
697 |
begin
|
698 |
{merge the hours, minutes, and seconds into the picture}
|
699 |
StTimeToHMS(T, Hours, Minutes, Seconds);
|
700 |
Result := Picture;
|
701 |
|
702 |
{check for TimeOnly}
|
703 |
OK := StrChPosL(Result, TimeOnly, TPos);
|
704 |
if OK then begin
|
705 |
if (Hours >= 12) then
|
706 |
P := t2359
|
707 |
else
|
708 |
P := t1159;
|
709 |
if (Length(t1159) > 0) and (Length(t2359) > 0) then
|
710 |
case Hours of
|
711 |
0 : Hours := 12;
|
712 |
13..23 : Dec(Hours, 12);
|
713 |
end;
|
714 |
end;
|
715 |
|
716 |
if T = BadTime then begin
|
717 |
{map picture characters to spaces}
|
718 |
Result := SubstChar(Result, HourOnly, ' ');
|
719 |
Result := SubstChar(Result, MinOnly, ' ');
|
720 |
Result := SubstChar(Result, SecOnly, ' ');
|
721 |
end
|
722 |
else begin
|
723 |
{merge the numbers into the picture}
|
724 |
MergeIntoPicture(Result, HourOnly, Hours);
|
725 |
MergeIntoPicture(Result, MinOnly, Minutes);
|
726 |
MergeIntoPicture(Result, SecOnly, Seconds);
|
727 |
end;
|
728 |
|
729 |
{map colons}
|
730 |
Result := SubstChar(Result, TimeColon, wColonChar);
|
731 |
|
732 |
{plug in AM/PM string if appropriate}
|
733 |
if OK then begin
|
734 |
if (Length(t1159) = 0) and (Length(t2359) = 0) then begin
|
735 |
C := SubstCharSim(Result[TPos], TimeOnly, ' ');
|
736 |
Result[TPos] := C[1];
|
737 |
end else if (T = BadTime) and (Length(t1159) = 0) then begin
|
738 |
C := SubstCharSim(Result[TPos], TimeOnly, ' ');
|
739 |
Result[TPos] := C[1];
|
740 |
end else begin
|
741 |
I := 1;
|
742 |
L := Length(P);
|
743 |
// while (I <= L) and (Result[TPos] = TimeOnly) do begin {!!.01} {!!.03}
|
744 |
while (I <= L) and {!!.03}
|
745 |
(TPos <= Length(Result)) and (Result[TPos] = TimeOnly) do {!!.03}
|
746 |
begin {!!.03}
|
747 |
Result[TPos] := P[I];
|
748 |
Inc(I);
|
749 |
Inc(TPos);
|
750 |
end;
|
751 |
end;
|
752 |
end;
|
753 |
|
754 |
if Pack and (T <> BadTime) then
|
755 |
Result := PackResult(Picture, Result);
|
756 |
end;
|
757 |
|
758 |
function StTimeToTimeString(const Picture : string; const T : TStTime;
|
759 |
Pack : Boolean) : string;
|
760 |
{-Convert T to a string of the form indicated by Picture}
|
761 |
begin
|
762 |
Result := TimeToTimeStringPrim(Picture, T, Pack, w1159, w2359);
|
763 |
end;
|
764 |
|
765 |
function StTimeToAmPmString(const Picture : string; const T : TStTime;
|
766 |
Pack : Boolean) : string;
|
767 |
{-Convert T to a string of the form indicated by Picture. Times are always
|
768 |
displayed in am/pm format.}
|
769 |
const
|
770 |
t1159 = 'AM';
|
771 |
t2359 = 'PM';
|
772 |
var
|
773 |
P : Cardinal;
|
774 |
begin
|
775 |
Result := Picture;
|
776 |
if NOT (StrChPosL(Result, TimeOnly, P)) then
|
777 |
Result := Result + TimeOnly;
|
778 |
Result := TimeToTimeStringPrim(Result, T, Pack, t1159, t2359);
|
779 |
end;
|
780 |
|
781 |
function CurrentTime : TStTime;
|
782 |
{-Returns current time in seconds since midnight}
|
783 |
begin
|
784 |
Result := Trunc(SysUtils.Time * SecondsInDay);
|
785 |
end;
|
786 |
|
787 |
function CurrentTimeString(const Picture : string; Pack : Boolean) : string;
|
788 |
{-Returns current time as a string of the specified form}
|
789 |
begin
|
790 |
Result := StTimeToTimeString(Picture, CurrentTime, Pack);
|
791 |
end;
|
792 |
|
793 |
function MaskCharCount(const P : string; MC : Char) : Integer; {!!.02}
|
794 |
var
|
795 |
I, R,
|
796 |
Len : Cardinal;
|
797 |
OK : Boolean;
|
798 |
begin
|
799 |
OK := StrChPosL(P, MC, I);
|
800 |
R := Ord(OK);
|
801 |
Len := Length(P);
|
802 |
if OK then
|
803 |
while (I+R <= Len) and (P[I+R] = MC) do {!!.01}
|
804 |
Inc(R);
|
805 |
Result := R;
|
806 |
end;
|
807 |
|
808 |
function InternationalDate(ForceCentury : Boolean) : string;
|
809 |
{-Return a picture mask for a date string, based on Windows' int'l info}
|
810 |
|
811 |
procedure FixMask(MC : Char; DL : Integer);
|
812 |
var
|
813 |
I, J, AL, D : Cardinal;
|
814 |
MCT : Char;
|
815 |
OK : Boolean;
|
816 |
begin
|
817 |
{find number of matching characters}
|
818 |
OK := StrChPosL(Result, MC, I);
|
819 |
MCT := MC;
|
820 |
if not OK then begin
|
821 |
MCT := StBase.UpCase(MC);
|
822 |
OK := StrChPosL(Result, MCT, I);
|
823 |
end;
|
824 |
if NOT OK then
|
825 |
Exit;
|
826 |
|
827 |
D := DL;
|
828 |
{pad substring to desired length}
|
829 |
AL := MaskCharCount(Result, MCT);
|
830 |
if AL < D then
|
831 |
for J := 1 to D-AL do
|
832 |
Result := StrChInsertL(Result, MCT, I);
|
833 |
|
834 |
if MC <> YearOnly then begin
|
835 |
{choose blank/zero padding}
|
836 |
case AL of
|
837 |
1 : if MCT = MC then
|
838 |
Result := SubstCharSim(Result, MCT, StBase.UpCase(MCT));
|
839 |
2 : if MCT <> MC then
|
840 |
Result := SubstCharSim(Result, MCT, MC);
|
841 |
end;
|
842 |
end;
|
843 |
end;
|
844 |
|
845 |
begin
|
846 |
{copy Windows mask into our var}
|
847 |
Result := wShortDate;
|
848 |
|
849 |
{if single Day marker, make double}
|
850 |
FixMask(DayOnly, 2);
|
851 |
|
852 |
{if single Month marker, make double}
|
853 |
FixMask(MonthOnly, 2);
|
854 |
|
855 |
{force yyyy if desired}
|
856 |
FixMask(YearOnly, 2 shl Ord(ForceCentury));
|
857 |
end;
|
858 |
|
859 |
|
860 |
function InternationalLongDate(ShortNames : Boolean;
|
861 |
ExcludeDOW : Boolean) : string;
|
862 |
{-Return a picture mask for a date string, based on Windows' int'l info}
|
863 |
var
|
864 |
I, WC : Cardinal;
|
865 |
OK,
|
866 |
Stop : Boolean;
|
867 |
Temp : string[81];
|
868 |
|
869 |
function LongestMonthName : Integer;
|
870 |
var
|
871 |
L, I : Integer;
|
872 |
begin
|
873 |
L := 0;
|
874 |
for I := 1 to 12 do
|
875 |
L := Maxword(L, Length({$IFDEF DELPHIXE2}FormatSettings.{$ENDIF}LongMonthNames[I]));
|
876 |
LongestMonthName := L;
|
877 |
end;
|
878 |
|
879 |
function LongestDayName : Integer;
|
880 |
var
|
881 |
D : TStDayType;
|
882 |
L : Integer;
|
883 |
begin
|
884 |
L := 0;
|
885 |
for D := Sunday to Saturday do
|
886 |
L := Maxword(L, Length({$IFDEF DELPHIXE2}FormatSettings.{$ENDIF}LongDayNames[Ord(D)+1]));
|
887 |
LongestDayName := L;
|
888 |
end;
|
889 |
|
890 |
procedure FixMask(MC : Char; DL : Integer);
|
891 |
var
|
892 |
I, J, AL, D : Cardinal;
|
893 |
MCT : Char;
|
894 |
begin
|
895 |
{find first matching mask character}
|
896 |
OK := StrChPosS(Temp, MC, I);
|
897 |
MCT := MC;
|
898 |
if NOT OK then begin
|
899 |
MCT := StBase.UpCase(MC);
|
900 |
OK := StrChPosS(Temp, MCT, I);
|
901 |
end;
|
902 |
if NOT OK then
|
903 |
Exit;
|
904 |
|
905 |
D := DL;
|
906 |
{pad substring to desired length}
|
907 |
AL := MaskCharCount(Temp, MCT);
|
908 |
if AL < D then begin
|
909 |
for J := 1 to D-AL do
|
910 |
Temp := StrChInsertL(Temp, MCT, I);
|
911 |
end else if (AL > D) then
|
912 |
Temp := StrStDeleteL(Temp, I, AL-D);
|
913 |
|
914 |
if MC <> YearOnly then
|
915 |
{choose blank/zero padding}
|
916 |
case AL of
|
917 |
1 : if MCT = MC then
|
918 |
Temp := SubstCharSim(Temp, MCT, StBase.UpCase(MCT));
|
919 |
2 : if MCT <> MC then
|
920 |
Temp := SubstCharSim(Temp, MCT, MC);
|
921 |
end;
|
922 |
end;
|
923 |
|
924 |
begin
|
925 |
{copy Windows mask into temporary var}
|
926 |
Temp := wLongDate;
|
927 |
|
928 |
if ExcludeDOW then begin
|
929 |
{remove day-of-week and any junk that follows}
|
930 |
if (StrChPosS(Temp, WeekDayOnly,I)) then begin
|
931 |
Stop := False;
|
932 |
WC := I+1;
|
933 |
while (WC <= Length(Temp)) AND (NOT Stop) do
|
934 |
begin
|
935 |
if LoCase(Temp[WC]) in [MonthOnly,DayOnly,YearOnly,NameOnly] then
|
936 |
Stop := TRUE
|
937 |
else
|
938 |
Inc(WC);
|
939 |
end;
|
940 |
if (NOT ShortNames) then
|
941 |
Dec(WC);
|
942 |
Temp := StrStDeleteS(Temp, I, WC);
|
943 |
end;
|
944 |
end
|
945 |
else if ShortNames then
|
946 |
FixMask(WeekDayOnly, 3)
|
947 |
else if MaskCharCount(Temp, WeekdayOnly) = 4 then
|
948 |
FixMask(WeekDayOnly, LongestDayName);
|
949 |
|
950 |
{fix month names}
|
951 |
if ShortNames then
|
952 |
FixMask(NameOnly, 3)
|
953 |
else if MaskCharCount(Temp, NameOnly) = 4 then
|
954 |
FixMask(NameOnly, LongestMonthName);
|
955 |
|
956 |
{if single Day marker, make double}
|
957 |
FixMask(DayOnly, 2);
|
958 |
|
959 |
{if single Month marker, make double}
|
960 |
FixMask(MonthOnly, 2);
|
961 |
|
962 |
{force yyyy}
|
963 |
FixMask(YearOnly, 4);
|
964 |
|
965 |
Result := Temp;
|
966 |
end;
|
967 |
|
968 |
function InternationalTime(ShowSeconds : Boolean) : string;
|
969 |
{-Return a picture mask for a time string, based on Windows' int'l info}
|
970 |
var
|
971 |
ML,
|
972 |
I : Integer;
|
973 |
begin
|
974 |
{format the default string}
|
975 |
|
976 |
SetLength(Result,21);
|
977 |
Result := 'hh:mm:ss';
|
978 |
if not wTLZero then
|
979 |
Result[1] := HourOnlyU;
|
980 |
|
981 |
{show seconds?}
|
982 |
if not ShowSeconds then
|
983 |
SetLength(Result,5);
|
984 |
|
985 |
{handle international AM/PM markers}
|
986 |
if w12Hour then begin
|
987 |
ML := Maxword(Length(w1159), Length(w2359));
|
988 |
if (ML <> 0) then begin
|
989 |
AppendChar(Result,' ');
|
990 |
for I := 1 to ML do
|
991 |
AppendChar(Result, TimeOnly);
|
992 |
end;
|
993 |
end;
|
994 |
end;
|
995 |
|
996 |
procedure SetDefaultYear;
|
997 |
{-Initialize DefaultYear and DefaultMonth}
|
998 |
var
|
999 |
Month, Day : Word;
|
1000 |
T : TDateTime;
|
1001 |
W : Word;
|
1002 |
begin
|
1003 |
T := Now;
|
1004 |
W := DefaultYear;
|
1005 |
DecodeDate(T,W,Month,Day);
|
1006 |
DefaultYear := W;
|
1007 |
DefaultMonth := Month;
|
1008 |
end;
|
1009 |
|
1010 |
procedure ResetInternationalInfo;
|
1011 |
var
|
1012 |
I : Integer;
|
1013 |
S : array[0..20] of char;
|
1014 |
|
1015 |
procedure ExtractSubString(SubChar : Char; Dest : string);
|
1016 |
var
|
1017 |
I, L, P : Cardinal;
|
1018 |
begin
|
1019 |
// SetLength(Dest,sizeof(wldSub1));
|
1020 |
// FillChar(Dest[1], SizeOf(wldSub1), 0);
|
1021 |
Dest := StringOfChar(#0, Succ(High(wldSub1))); //SZ: not length! [*]
|
1022 |
if NOT (StrChPosS(wLongDate, '''',I)) then
|
1023 |
Exit;
|
1024 |
|
1025 |
{delete the first quote}
|
1026 |
wLongDate := StrChDeleteS(wLongDate, I);
|
1027 |
|
1028 |
{assure that there is another quote}
|
1029 |
if NOT (StrChPosS(wLongDate, '''',P)) then
|
1030 |
Exit;
|
1031 |
|
1032 |
{copy substring into Dest, replace substring with SubChar}
|
1033 |
L := 1;
|
1034 |
while wLongDate[I] <> '''' do
|
1035 |
if L < SizeOf(wldSub1) then begin
|
1036 |
Dest[L] := wLongDate[I];
|
1037 |
Inc(L);
|
1038 |
wLongDate[I] := SubChar;
|
1039 |
Inc(I);
|
1040 |
end else
|
1041 |
wLongDate := StrChDeleteL(wLongDate, I);
|
1042 |
|
1043 |
{delete the second quote}
|
1044 |
wLongDate := StrChDeleteL(wLongDate, I);
|
1045 |
end;
|
1046 |
|
1047 |
begin
|
1048 |
wTLZero := {$IFDEF DELPHIXE2}FormatSettings.{$ENDIF}LongTimeFormat[2] = 'h';
|
1049 |
w12Hour := {$IFDEF DELPHIXE2}FormatSettings.{$ENDIF}LongTimeFormat[length({$IFDEF DELPHIXE2}FormatSettings.{$ENDIF}LongTimeFormat)] = 'M';
|
1050 |
|
1051 |
wColonChar := {$IFDEF DELPHIXE2}FormatSettings.{$ENDIF}TimeSeparator;
|
1052 |
wSlashChar := {$IFDEF DELPHIXE2}FormatSettings.{$ENDIF}DateSeparator;
|
1053 |
|
1054 |
GetProfileString('intl','s1159','AM', S, Length(S));
|
1055 |
w1159 := StrPas(S);
|
1056 |
GetProfileString('intl','s2359','PM', S, Length(S));
|
1057 |
w2359 := StrPas(S);
|
1058 |
|
1059 |
{get short date mask and fix it up}
|
1060 |
wShortDate := {$IFDEF DELPHIXE2}FormatSettings.{$ENDIF}ShortDateFormat;
|
1061 |
for I := 1 to Length(wShortDate) do
|
1062 |
if (wShortDate[I] = wSlashChar) then
|
1063 |
wShortDate[I] := '/';
|
1064 |
|
1065 |
{get long date mask and fix it up}
|
1066 |
wLongDate := {$IFDEF DELPHIXE2}FormatSettings.{$ENDIF}LongDateFormat;
|
1067 |
ExtractSubString(LongDateSub1, wldSub1);
|
1068 |
ExtractSubString(LongDateSub2, wldSub2);
|
1069 |
ExtractSubString(LongDateSub3, wldSub3);
|
1070 |
|
1071 |
{replace ddd/dddd with www/wwww}
|
1072 |
I := pos('ddd',wLongDate);
|
1073 |
if I > 0 then begin
|
1074 |
while wLongDate[I] = 'd' do begin
|
1075 |
wLongDate[I] := 'w';
|
1076 |
Inc(I);
|
1077 |
end;
|
1078 |
end;
|
1079 |
|
1080 |
{replace MMM/MMMM with nnn/nnnn}
|
1081 |
if pos('MMM',wLongDate) > 0 then
|
1082 |
while (pos('M',wLongDate) > 0) do
|
1083 |
wLongDate[pos('M',wLongDate)] := 'n';
|
1084 |
|
1085 |
{deal with oddities concerning . and ,}
|
1086 |
for I := 1 to Length(wLongDate)-1 do begin
|
1087 |
case wLongDate[I] of
|
1088 |
'.', ',' :
|
1089 |
if wLongDate[I+1] <> ' ' then
|
1090 |
wLongDate := StrChInsertS(wLongDate, ' ', I+1);
|
1091 |
end;
|
1092 |
end;
|
1093 |
end;
|
1094 |
|
1095 |
|
1096 |
initialization
|
1097 |
{initialize DefaultYear and DefaultMonth}
|
1098 |
SetDefaultYear;
|
1099 |
ResetInternationalInfo;
|
1100 |
end.
|