blob: 55228687bcf86bb394b1e0efcee917fb48044501 [file] [log] [blame]
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -07001// Copyright 2014 PDFium Authors. All rights reserved.
2// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
4
5// Original code copyright 2014 Foxit Software Inc. http://www.foxitsoftware.com
6
7#include "../../include/javascript/JavaScript.h"
8#include "../../include/javascript/IJavaScript.h"
9#include "../../include/javascript/JS_Define.h"
10#include "../../include/javascript/JS_Object.h"
11#include "../../include/javascript/JS_Value.h"
12#include "../../include/javascript/PublicMethods.h"
13#include "../../include/javascript/JS_EventHandler.h"
14#include "../../include/javascript/resource.h"
15#include "../../include/javascript/JS_Context.h"
16#include "../../include/javascript/JS_Value.h"
17#include "../../include/javascript/util.h"
18#include "../../include/javascript/Field.h"
19#include "../../include/javascript/color.h"
20#include "../../include/javascript/JS_Runtime.h"
21
22static v8::Isolate* GetIsolate(IFXJS_Context* cc)
23{
24 CJS_Context* pContext = (CJS_Context *)cc;
25 ASSERT(pContext != NULL);
26
27 CJS_Runtime* pRuntime = pContext->GetJSRuntime();
28 ASSERT(pRuntime != NULL);
29
30 return pRuntime->GetIsolate();
31}
32
33
34/* -------------------------------- CJS_PublicMethods -------------------------------- */
35
36#define DOUBLE_CORRECT 0.000000000000001
37
38BEGIN_JS_STATIC_GLOBAL_FUN(CJS_PublicMethods)
39 JS_STATIC_GLOBAL_FUN_ENTRY(AFNumber_Format,6)
40 JS_STATIC_GLOBAL_FUN_ENTRY(AFNumber_Keystroke,6)
41 JS_STATIC_GLOBAL_FUN_ENTRY(AFPercent_Format,2)
42 JS_STATIC_GLOBAL_FUN_ENTRY(AFPercent_Keystroke,2)
43 JS_STATIC_GLOBAL_FUN_ENTRY(AFDate_FormatEx,1)
44 JS_STATIC_GLOBAL_FUN_ENTRY(AFDate_KeystrokeEx,1)
45 JS_STATIC_GLOBAL_FUN_ENTRY(AFDate_Format,1)
46 JS_STATIC_GLOBAL_FUN_ENTRY(AFDate_Keystroke,1)
47 JS_STATIC_GLOBAL_FUN_ENTRY(AFTime_FormatEx,1)
48 JS_STATIC_GLOBAL_FUN_ENTRY(AFTime_KeystrokeEx,1)
49 JS_STATIC_GLOBAL_FUN_ENTRY(AFTime_Format,1)
50 JS_STATIC_GLOBAL_FUN_ENTRY(AFTime_Keystroke,1)
51 JS_STATIC_GLOBAL_FUN_ENTRY(AFSpecial_Format,1)
52 JS_STATIC_GLOBAL_FUN_ENTRY(AFSpecial_Keystroke,1)
53 JS_STATIC_GLOBAL_FUN_ENTRY(AFSpecial_KeystrokeEx,1)
54 JS_STATIC_GLOBAL_FUN_ENTRY(AFSimple,3)
55 JS_STATIC_GLOBAL_FUN_ENTRY(AFMakeNumber,1)
56 JS_STATIC_GLOBAL_FUN_ENTRY(AFSimple_Calculate,2)
57 JS_STATIC_GLOBAL_FUN_ENTRY(AFRange_Validate,4)
58 JS_STATIC_GLOBAL_FUN_ENTRY(AFMergeChange,1)
59 JS_STATIC_GLOBAL_FUN_ENTRY(AFParseDateEx,2)
60 JS_STATIC_GLOBAL_FUN_ENTRY(AFExtractNums,1)
61END_JS_STATIC_GLOBAL_FUN()
62
63IMPLEMENT_JS_STATIC_GLOBAL_FUN(CJS_PublicMethods)
64
65struct stru_TbConvert
66{
67 FX_LPCSTR lpszJSMark;
68 FX_LPCSTR lpszCppMark;
69};
70
71static const stru_TbConvert fcTable[] = {"mmmm","%B",
72 "mmm", "%b",
73 "mm", "%m",
74 //"m"
75 "dddd","%A",
76 "ddd", "%a",
77 "dd", "%d",
78 //"d", "%w",
79 "yyyy","%Y",
80 "yy", "%y",
81 "HH", "%H",
82 //"H"
83 "hh", "%I",
84 //"h"
85 "MM", "%M",
86 //"M"
87 "ss", "%S",
88 //"s
89 "tt", "%p"
90 //"t"
91};
92
93static FX_LPCWSTR months[] =
94{
95 (FX_LPCWSTR)L"Jan", (FX_LPCWSTR)L"Feb", (FX_LPCWSTR)L"Mar", (FX_LPCWSTR)L"Apr", (FX_LPCWSTR)L"May", (FX_LPCWSTR)L"Jun", (FX_LPCWSTR)L"Jul", (FX_LPCWSTR)L"Aug", (FX_LPCWSTR)L"Sep", (FX_LPCWSTR)L"Oct", (FX_LPCWSTR)L"Nov", (FX_LPCWSTR)L"Dec"
96};
97
98static FX_LPCWSTR fullmonths[] =
99{
100 (FX_LPCWSTR)L"January", (FX_LPCWSTR)L"February", (FX_LPCWSTR)L"March", (FX_LPCWSTR)L"April", (FX_LPCWSTR)L"May", (FX_LPCWSTR)L"June", (FX_LPCWSTR)L"July", (FX_LPCWSTR)L"August", (FX_LPCWSTR)L"September", (FX_LPCWSTR)L"October", (FX_LPCWSTR)L"November", (FX_LPCWSTR)L"December"
101};
102
103FX_BOOL CJS_PublicMethods::IsNumber(FX_LPCWSTR string)
104{
105 CFX_WideString sTrim = StrTrim(string);
106 FX_LPCWSTR pTrim = sTrim;
107 FX_LPCWSTR p = pTrim;
108
109
110 FX_BOOL bDot = FALSE;
111 FX_BOOL bKXJS = FALSE;
112
113 wchar_t c;
114 while ((c = *p))
115 {
116 if (c == '.' || c == ',')
117 {
118 if (bDot) return FALSE;
119 bDot = TRUE;
120 }
121 else if (c == '-' || c == '+')
122 {
123 if (p != pTrim)
124 return FALSE;
125 }
126 else if (c == 'e' || c == 'E')
127 {
128 if (bKXJS) return FALSE;
129
130 p++;
131 c = *p;
132 if (c == '+' || c == '-')
133 {
134 bKXJS = TRUE;
135 }
136 else
137 {
138 return FALSE;
139 }
140 }
141 else if (!IsDigit(c))
142 {
143 return FALSE;
144 }
145 p++;
146 }
147
148 return TRUE;
149}
150
151FX_BOOL CJS_PublicMethods::IsDigit(wchar_t ch)
152{
153 return (ch >= L'0' && ch <= L'9');
154}
155
156FX_BOOL CJS_PublicMethods::IsDigit(char ch)
157{
158 return (ch >= '0' && ch <= '9');
159}
160
161FX_BOOL CJS_PublicMethods::IsAlphabetic(wchar_t ch)
162{
163 return ((ch >= L'a' && ch <= L'z') || (ch >= L'A' && ch <= L'Z'));
164}
165
166FX_BOOL CJS_PublicMethods::IsAlphaNumeric(wchar_t ch)
167{
168 return (IsDigit(ch) || IsAlphabetic(ch));
169}
170
171FX_BOOL CJS_PublicMethods::maskSatisfied(wchar_t c_Change,wchar_t c_Mask)
172{
173 switch (c_Mask)
174 {
175 case L'9':
176 return IsDigit(c_Change);
177 case L'A':
178 return IsAlphabetic(c_Change);
179 case L'O':
180 return IsAlphaNumeric(c_Change);
181 case L'X':
182 return TRUE;
183 default:
184 return (c_Change == c_Mask);
185 }
186}
187
188FX_BOOL CJS_PublicMethods::isReservedMaskChar(wchar_t ch)
189{
190 return ch == L'9' || ch == L'A' || ch == L'O' || ch == L'X';
191}
192
193double CJS_PublicMethods::AF_Simple(FX_LPCWSTR sFuction, double dValue1, double dValue2)
194{
195 if (FXSYS_wcsicmp(sFuction,(FX_LPCWSTR)L"AVG") == 0 || FXSYS_wcsicmp(sFuction,(FX_LPCWSTR)L"SUM") == 0)
196 {
197 return dValue1 + dValue2;
198 }
199 else if (FXSYS_wcsicmp(sFuction, (FX_LPCWSTR)L"PRD") == 0)
200 {
201 return dValue1 * dValue2;
202 }
203 else if (FXSYS_wcsicmp(sFuction,(FX_LPCWSTR)L"MIN") == 0)
204 {
205 return FX_MIN(dValue1, dValue2);
206 }
207 else if (FXSYS_wcsicmp(sFuction,(FX_LPCWSTR)L"MAX") == 0)
208 {
209 return FX_MAX(dValue1, dValue2);
210 }
211
212 return dValue1;
213}
214
215CFX_WideString CJS_PublicMethods::StrLTrim(FX_LPCWSTR pStr)
216{
217 while (*pStr && *pStr == L' ') pStr++;
218
219 return pStr;
220}
221
222CFX_WideString CJS_PublicMethods::StrRTrim(FX_LPCWSTR pStr)
223{
224 FX_LPCWSTR p = pStr;
225
226 while (*p) p++;
227 p--;
228 if (p >= pStr)
229 {
230 while (*p && *p == L' ') p--;
231 p++;
232 return CFX_WideString(pStr,p-pStr);
233 }
234 return L"";
235}
236
237CFX_WideString CJS_PublicMethods::StrTrim(FX_LPCWSTR pStr)
238{
239 return StrRTrim(StrLTrim(pStr));
240}
241
242CFX_ByteString CJS_PublicMethods::StrLTrim(FX_LPCSTR pStr)
243{
244 while (*pStr && *pStr == ' ') pStr++;
245
246 return pStr;
247}
248
249CFX_ByteString CJS_PublicMethods::StrRTrim(FX_LPCSTR pStr)
250{
251 FX_LPCSTR p = pStr;
252
253 while (*p) p++;
254 p--;
255 if (p >= pStr)
256 {
257 while (*p && *p == ' ') p--;
258 p++;
259 return CFX_ByteString(pStr,p-pStr);
260 }
261 return "";
262}
263
264CFX_ByteString CJS_PublicMethods::StrTrim(FX_LPCSTR pStr)
265{
266 return StrRTrim(StrLTrim(pStr));
267}
268
269double CJS_PublicMethods::ParseNumber(FX_LPCWSTR swSource, FX_BOOL& bAllDigits, FX_BOOL& bDot, FX_BOOL& bSign, FX_BOOL& bKXJS)
270{
271 bDot = FALSE;
272 bSign = FALSE;
273 bKXJS = FALSE;
274
275 FX_BOOL bDigitExist = FALSE;
276
277 FX_LPCWSTR p = swSource;
278 wchar_t c;
279
280 FX_LPCWSTR pStart = NULL;
281 FX_LPCWSTR pEnd = NULL;
282
283 while ((c = *p))
284 {
285 if (!pStart && c != L' ')
286 {
287 pStart = p;
288 }
289
290 pEnd = p;
291 p++;
292 }
293
294 if (!pStart)
295 {
296 bAllDigits = FALSE;
297 return 0;
298 }
299
300 while (pEnd != pStart)
301 {
302 if (*pEnd == L' ')
303 pEnd --;
304 else
305 break;
306 }
307
308 double dRet = 0;
309 p = pStart;
310 bAllDigits = TRUE;
311 CFX_WideString swDigits;
312
313 while (p <= pEnd)
314 {
315 c = *p;
316
317 if (IsDigit(c))
318 {
319 swDigits += c;
320 bDigitExist = TRUE;
321 }
322 else
323 {
324 switch (c)
325 {
326 case L' ':
327 bAllDigits = FALSE;
328 break;
329 case L'.':
330 case L',':
331 if (!bDot)
332 {
333 if (bDigitExist)
334 {
335 swDigits += L'.';
336 }
337 else
338 {
339 swDigits += L'0';
340 swDigits += L'.';
341 bDigitExist = TRUE;
342 }
343
344 bDot = TRUE;
345 break;
346 }
347 case 'e':
348 case 'E':
349 if (!bKXJS)
350 {
351 p++;
352 c = *p;
353 if (c == '+' || c == '-')
354 {
355 bKXJS = TRUE;
356 swDigits += 'e';
357 swDigits += c;
358 }
359 break;
360 }
361 case L'-':
362 if (!bDigitExist && !bSign)
363 {
364 swDigits += c;
365 bSign = TRUE;
366 break;
367 }
368 default:
369 bAllDigits = FALSE;
370
371 if (p != pStart && !bDot && bDigitExist)
372 {
373 swDigits += L'.';
374 bDot = TRUE;
375 }
376 else
377 {
378 bDot = FALSE;
379 bDigitExist = FALSE;
380 swDigits = L"";
381 }
382 break;
383 }
384 }
385
386 p++;
387 }
388
389 if (swDigits.GetLength() > 0 && swDigits.GetLength() < 17)
390 {
391 CFX_ByteString sDigits = swDigits.UTF8Encode();
392
393 if (bKXJS)
394 {
395 dRet = atof(sDigits);
396 }
397 else
398 {
399 if (bDot)
400 {
401 char* pStopString;
402 dRet = ::strtod(sDigits, &pStopString);
403 }
404 else
405 {
406 dRet = atol(sDigits);
407 }
408 }
409
410 }
411
412 return dRet;
413}
414
415double CJS_PublicMethods::ParseStringToNumber(FX_LPCWSTR swSource)
416{
417 FX_BOOL bAllDigits = FALSE;
418 FX_BOOL bDot = FALSE;
419 FX_BOOL bSign = FALSE;
420 FX_BOOL bKXJS = FALSE;
421
422 return ParseNumber(swSource, bAllDigits, bDot, bSign, bKXJS);
423}
424
425FX_BOOL CJS_PublicMethods::ConvertStringToNumber(FX_LPCWSTR swSource, double & dRet, FX_BOOL & bDot)
426{
427 FX_BOOL bAllDigits = FALSE;
428 FX_BOOL bSign = FALSE;
429 FX_BOOL bKXJS = FALSE;
430
431 dRet = ParseNumber(swSource, bAllDigits, bDot, bSign, bKXJS);
432
433 return bAllDigits;
434}
435
436CJS_Array CJS_PublicMethods::AF_MakeArrayFromList(v8::Isolate* isolate, CJS_Value val)
437{
438 CJS_Array StrArray(isolate);
439 if(val.IsArrayObject())
440 {
441 val.ConvertToArray(StrArray);
442 return StrArray;
443 }
444 CFX_WideString wsStr = val.operator CFX_WideString();
445 CFX_ByteString t = CFX_ByteString::FromUnicode(wsStr);
446 const char * p = (const char *)t;
447
448
449 int ch = ',' ;
450 int nIndex = 0;
451
452 while (*p)
453 {
454 const char * pTemp = strchr(p, ch);
455 if (pTemp == NULL)
456 {
457 StrArray.SetElement(nIndex, CJS_Value(isolate,(FX_LPCSTR)StrTrim(p)));
458 break;
459 }
460 else
461 {
462 char * pSub = new char[pTemp - p + 1];
463 strncpy(pSub, p, pTemp - p);
464 *(pSub + (pTemp - p)) = '\0';
465
466 StrArray.SetElement(nIndex, CJS_Value(isolate,(FX_LPCSTR)StrTrim(pSub)));
467 delete []pSub;
468
469 nIndex ++;
470 p = ++pTemp;
471 }
472
473 }
474 return StrArray;
475}
476
477int CJS_PublicMethods::ParseStringInteger(const CFX_WideString& string,int nStart,int& nSkip, int nMaxStep)
478{
479 int nRet = 0;
480 nSkip = 0;
481 for (int i=nStart, sz=string.GetLength(); i < sz; i++)
482 {
483 if (i-nStart > 10)
484 break;
485
486 FX_WCHAR c = string.GetAt(i);
487 if (IsDigit((wchar_t)c))
488 {
489 nRet = nRet * 10 + (c - '0');
490 nSkip = i - nStart + 1;
491 if (nSkip >= nMaxStep)
492 break;
493 }
494 else
495 break;
496 }
497
498 return nRet;
499}
500
501CFX_WideString CJS_PublicMethods::ParseStringString(const CFX_WideString& string, int nStart, int& nSkip)
502{
503 CFX_WideString swRet;
504 nSkip = 0;
505 for (int i=nStart, sz=string.GetLength(); i < sz; i++)
506 {
507 FX_WCHAR c = string.GetAt(i);
508 if ((c >= L'a' && c <= L'z') || (c >= L'A' && c <= L'Z'))
509 {
510 swRet += c;
511 nSkip = i - nStart + 1;
512 }
513 else
514 break;
515 }
516
517 return swRet;
518}
519
520double CJS_PublicMethods::ParseNormalDate(const CFX_WideString & value, FX_BOOL& bWrongFormat)
521{
522 double dt = JS_GetDateTime();
523
524 int nYear = JS_GetYearFromTime(dt);
525 int nMonth = JS_GetMonthFromTime(dt) + 1;
526 int nDay = JS_GetDayFromTime(dt);
527 int nHour = JS_GetHourFromTime(dt);
528 int nMin = JS_GetMinFromTime(dt);
529 int nSec = JS_GetSecFromTime(dt);
530
531 int number[3];
532
533 int nSkip = 0;
534 int nLen = value.GetLength();
535 int nIndex = 0;
536 int i = 0;
537 while (i < nLen)
538 {
539 if (nIndex > 2) break;
540
541 FX_WCHAR c = value.GetAt(i);
542 if (IsDigit((wchar_t)c))
543 {
544 number[nIndex++] = ParseStringInteger(value, i, nSkip, 4);
545 i += nSkip;
546 }
547 else
548 {
549 i ++;
550 }
551 }
552
553 if (nIndex == 2)
554 {
555 // case2: month/day
556 // case3: day/month
557 if ((number[0] >= 1 && number[0] <= 12) && (number[1] >= 1 && number[1] <= 31))
558 {
559 nMonth = number[0];
560 nDay = number[1];
561 }
562 else if ((number[0] >= 1 && number[0] <= 31) && (number[1] >= 1 && number[1] <= 12))
563 {
564 nDay = number[0];
565 nMonth = number[1];
566 }
567
568 bWrongFormat = FALSE;
569 }
570 else if (nIndex == 3)
571 {
572 // case1: year/month/day
573 // case2: month/day/year
574 // case3: day/month/year
575
576 if (number[0] > 12 && (number[1] >= 1 && number[1] <= 12) && (number[2] >= 1 && number[2] <= 31))
577 {
578 nYear = number[0];
579 nMonth = number[1];
580 nDay = number[2];
581 }
582 else if ((number[0] >= 1 && number[0] <= 12) && (number[1] >= 1 && number[1] <= 31) && number[2] > 31)
583 {
584 nMonth = number[0];
585 nDay = number[1];
586 nYear = number[2];
587 }
588 else if ((number[0] >= 1 && number[0] <= 31) && (number[1] >= 1 && number[1] <= 12) && number[2] > 31)
589 {
590 nDay = number[0];
591 nMonth = number[1];
592 nYear = number[2];
593 }
594
595 bWrongFormat = FALSE;
596 }
597 else
598 {
599 bWrongFormat = TRUE;
600 return dt;
601 }
602
603 CFX_WideString swTemp;
604 swTemp.Format((FX_LPCWSTR)L"%d/%d/%d %d:%d:%d",nMonth,nDay,nYear,nHour,nMin,nSec);
605 return JS_DateParse(swTemp);
606}
607
608double CJS_PublicMethods::MakeRegularDate(const CFX_WideString & value, const CFX_WideString & format, FX_BOOL& bWrongFormat)
609{
610 double dt = JS_GetDateTime();
611
612 if (format.IsEmpty() || value.IsEmpty())
613 return dt;
614
615 int nYear = JS_GetYearFromTime(dt);
616 int nMonth = JS_GetMonthFromTime(dt) + 1;
617 int nDay = JS_GetDayFromTime(dt);
618 int nHour = JS_GetHourFromTime(dt);
619 int nMin = JS_GetMinFromTime(dt);
620 int nSec = JS_GetSecFromTime(dt);
621
622 int nYearSub = 99; //nYear - 2000;
623
624 FX_BOOL bPm = FALSE;
625 FX_BOOL bExit = FALSE;
626 bWrongFormat = FALSE;
Tom Sepez5ffacd62014-07-18 14:42:12 -0700627
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700628 int i=0;
629 int j=0;
630
631 while (i < format.GetLength())
632 {
633 if (bExit) break;
634
Tom Sepez5ffacd62014-07-18 14:42:12 -0700635 FX_WCHAR c = format.GetAt(i);
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700636 switch (c)
637 {
638 case ':':
639 case '.':
640 case '-':
641 case '\\':
642 case '/':
643 i++;
644 j++;
645 break;
Tom Sepez5ffacd62014-07-18 14:42:12 -0700646
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700647 case 'y':
648 case 'm':
649 case 'd':
650 case 'H':
651 case 'h':
652 case 'M':
653 case 's':
654 case 't':
655 {
656 int oldj = j;
657 int nSkip = 0;
Tom Sepez5ffacd62014-07-18 14:42:12 -0700658 int remaining = format.GetLength() - i - 1;
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700659
Tom Sepez5ffacd62014-07-18 14:42:12 -0700660 if (remaining == 0 || format.GetAt(i+1) != c)
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700661 {
662 switch (c)
663 {
664 case 'y':
665 i++;
666 j++;
667 break;
668 case 'm':
669 nMonth = ParseStringInteger(value, j, nSkip, 2);
670 i++;
671 j += nSkip;
672 break;
673 case 'd':
674 nDay = ParseStringInteger(value, j, nSkip, 2);
675 i++;
676 j += nSkip;
677 break;
678 case 'H':
679 nHour = ParseStringInteger(value, j, nSkip, 2);
680 i++;
681 j += nSkip;
682 break;
683 case 'h':
684 nHour = ParseStringInteger(value, j, nSkip, 2);
685 i++;
686 j += nSkip;
687 break;
688 case 'M':
689 nMin = ParseStringInteger(value, j, nSkip, 2);
690 i++;
691 j += nSkip;
692 break;
693 case 's':
694 nSec = ParseStringInteger(value, j, nSkip, 2);
695 i++;
696 j += nSkip;
697 break;
698 case 't':
Tom Sepez5ffacd62014-07-18 14:42:12 -0700699 bPm = (j < value.GetLength() && value.GetAt(j) == 'p');
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700700 i++;
701 j++;
702 break;
Tom Sepez5ffacd62014-07-18 14:42:12 -0700703 }
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700704 }
Tom Sepez5ffacd62014-07-18 14:42:12 -0700705 else if (remaining == 1 || format.GetAt(i+2) != c)
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700706 {
707 switch (c)
708 {
709 case 'y':
710 nYear = ParseStringInteger(value, j, nSkip, 4);
711 i += 2;
712 j += nSkip;
713 break;
714 case 'm':
715 nMonth = ParseStringInteger(value, j, nSkip, 2);
716 i += 2;
717 j += nSkip;
718 break;
719 case 'd':
720 nDay = ParseStringInteger(value, j, nSkip, 2);
721 i += 2;
722 j += nSkip;
723 break;
724 case 'H':
725 nHour = ParseStringInteger(value, j, nSkip, 2);
726 i += 2;
727 j += nSkip;
728 break;
729 case 'h':
730 nHour = ParseStringInteger(value, j, nSkip, 2);
731 i += 2;
732 j += nSkip;
733 break;
734 case 'M':
735 nMin = ParseStringInteger(value, j, nSkip, 2);
736 i += 2;
737 j += nSkip;
738 break;
739 case 's':
740 nSec = ParseStringInteger(value, j, nSkip, 2);
741 i += 2;
742 j += nSkip;
743 break;
744 case 't':
Tom Sepez5ffacd62014-07-18 14:42:12 -0700745 bPm = (j + 1 < value.GetLength() && value.GetAt(j) == 'p' && value.GetAt(j+1) == 'm');
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700746 i += 2;
747 j += 2;
748 break;
749 }
750 }
Tom Sepez5ffacd62014-07-18 14:42:12 -0700751 else if (remaining == 2 || format.GetAt(i+3) != c)
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700752 {
753 switch (c)
754 {
755 case 'm':
756 {
757 CFX_WideString sMonth = ParseStringString(value, j, nSkip);
758 FX_BOOL bFind = FALSE;
759 for (int m = 0; m < 12; m++)
760 {
761 if (sMonth.CompareNoCase(months[m]) == 0)
762 {
763 nMonth = m + 1;
764 i+=3;
765 j+=nSkip;
766 bFind = TRUE;
767 break;
768 }
769 }
Tom Sepez5ffacd62014-07-18 14:42:12 -0700770
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700771 if (!bFind)
772 {
773 nMonth = ParseStringInteger(value, j, nSkip, 3);
774 i+=3;
775 j += nSkip;
776 }
777 }
778 break;
779 case 'y':
780 break;
781 default:
782 i+=3;
783 j+=3;
784 break;
785 }
786 }
Tom Sepez5ffacd62014-07-18 14:42:12 -0700787 else if (remaining == 3 || format.GetAt(i+4) != c)
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700788 {
789 switch (c)
790 {
791
792
793 case 'y':
794 nYear = ParseStringInteger(value, j, nSkip, 4);
795 j += nSkip;
796 i += 4;
797 break;
798 case 'm':
799 {
800 FX_BOOL bFind = FALSE;
801
802 CFX_WideString sMonth = ParseStringString(value, j, nSkip);
803 sMonth.MakeLower();
804
805 for (int m = 0; m < 12; m++)
806 {
807 CFX_WideString sFullMonths = fullmonths[m];
808 sFullMonths.MakeLower();
809
810 if (sFullMonths.Find(sMonth, 0) != -1)
811 {
812 nMonth = m + 1;
813 i += 4;
814 j += nSkip;
815 bFind = TRUE;
816 break;
817 }
818 }
Tom Sepez5ffacd62014-07-18 14:42:12 -0700819
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700820 if (!bFind)
821 {
822 nMonth = ParseStringInteger(value, j, nSkip, 4);
823 i+=4;
824 j += nSkip;
825 }
826 }
827 break;
828 default:
829 i += 4;
830 j += 4;
831 break;
Tom Sepez5ffacd62014-07-18 14:42:12 -0700832 }
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700833 }
834 else
835 {
Tom Sepez5ffacd62014-07-18 14:42:12 -0700836 if (j >= value.GetLength() || format.GetAt(i) != value.GetAt(j))
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700837 {
838 bWrongFormat = TRUE;
839 bExit = TRUE;
840 }
841 i++;
842 j++;
843 }
Tom Sepez5ffacd62014-07-18 14:42:12 -0700844
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700845 if (oldj == j)
846 {
847 bWrongFormat = TRUE;
848 bExit = TRUE;
849 }
850 }
851
Tom Sepez5ffacd62014-07-18 14:42:12 -0700852 break;
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700853 default:
854 if (value.GetLength() <= j)
855 {
856 bExit = TRUE;
857 }
858 else if (format.GetAt(i) != value.GetAt(j))
859 {
860 bWrongFormat = TRUE;
861 bExit = TRUE;
862 }
863
864 i++;
865 j++;
866 break;
Tom Sepez5ffacd62014-07-18 14:42:12 -0700867 }
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700868 }
869
870 if (bPm) nHour += 12;
871
872 if (nYear >= 0 && nYear <= nYearSub)
873 nYear += 2000;
874
875 if (nMonth < 1 || nMonth > 12)
876 bWrongFormat = TRUE;
877
878 if (nDay < 1 || nDay > 31)
879 bWrongFormat = TRUE;
880
881 if (nHour < 0 || nHour > 24)
882 bWrongFormat = TRUE;
883
884 if (nMin < 0 || nMin > 60)
885 bWrongFormat = TRUE;
886
887 if (nSec < 0 || nSec > 60)
888 bWrongFormat = TRUE;
889
890 double dRet = 0;
891
892 if (bWrongFormat)
893 {
894 dRet = ParseNormalDate(value, bWrongFormat);
895 }
896 else
897 {
898 dRet = JS_MakeDate(JS_MakeDay(nYear,nMonth - 1,nDay),JS_MakeTime(nHour, nMin, nSec, 0));
899
900 if (JS_PortIsNan(dRet))
901 {
902 dRet = JS_DateParse(value);
903 }
904 }
905
906 if (JS_PortIsNan(dRet))
907 {
908 dRet = ParseNormalDate(value, bWrongFormat);
909 }
910
911 return dRet;
912
913}
914
915CFX_WideString CJS_PublicMethods::MakeFormatDate(double dDate, const CFX_WideString & format)
916{
917 CFX_WideString sRet = L"",sPart = L"";
918
919 int nYear = JS_GetYearFromTime(dDate);
920 int nMonth = JS_GetMonthFromTime(dDate) + 1;
921 int nDay = JS_GetDayFromTime(dDate);
922 int nHour = JS_GetHourFromTime(dDate);
923 int nMin = JS_GetMinFromTime(dDate);
924 int nSec = JS_GetSecFromTime(dDate);
925
926 int i = 0;
927 FX_WCHAR c;
928 while (i < format.GetLength())
929 {
930 c = format.GetAt(i);
931 sPart = L"";
932 switch (c)
933 {
934 case 'y':
935 case 'm':
936 case 'd':
937 case 'H':
938 case 'h':
939 case 'M':
940 case 's':
941 case 't':
942 if (format.GetAt(i+1) != c)
943 {
944 switch (c)
945 {
946 case 'y':
947 sPart += c;
948 break;
949 case 'm':
950 sPart.Format((FX_LPCWSTR)L"%d",nMonth);
951 break;
952 case 'd':
953 sPart.Format((FX_LPCWSTR)L"%d",nDay);
954 break;
955 case 'H':
956 sPart.Format((FX_LPCWSTR)L"%d",nHour);
957 break;
958 case 'h':
959 sPart.Format((FX_LPCWSTR)L"%d",nHour>12?nHour - 12:nHour);
960 break;
961 case 'M':
962 sPart.Format((FX_LPCWSTR)L"%d",nMin);
963 break;
964 case 's':
965 sPart.Format((FX_LPCWSTR)L"%d",nSec);
966 break;
967 case 't':
968 sPart += nHour>12?'p':'a';
969 break;
970 }
971 i++;
972 }
973 else if (format.GetAt(i+1) == c && format.GetAt(i+2) != c)
974 {
975 switch (c)
976 {
977 case 'y':
978 sPart.Format((FX_LPCWSTR)L"%02d",nYear - (nYear / 100) * 100);
979 break;
980 case 'm':
981 sPart.Format((FX_LPCWSTR)L"%02d",nMonth);
982 break;
983 case 'd':
984 sPart.Format((FX_LPCWSTR)L"%02d",nDay);
985 break;
986 case 'H':
987 sPart.Format((FX_LPCWSTR)L"%02d",nHour);
988 break;
989 case 'h':
990 sPart.Format((FX_LPCWSTR)L"%02d",nHour>12?nHour - 12:nHour);
991 break;
992 case 'M':
993 sPart.Format((FX_LPCWSTR)L"%02d",nMin);
994 break;
995 case 's':
996 sPart.Format((FX_LPCWSTR)L"%02d",nSec);
997 break;
998 case 't':
999 sPart = nHour>12? (FX_LPCWSTR)L"pm": (FX_LPCWSTR)L"am";
1000 break;
1001 }
1002 i+=2;
1003 }
1004 else if (format.GetAt(i+1) == c && format.GetAt(i+2) == c && format.GetAt(i+3) != c)
1005 {
1006 switch (c)
1007 {
1008 case 'm':
1009 i+=3;
1010 if (nMonth > 0&&nMonth <= 12)
1011 sPart += months[nMonth - 1];
1012 break;
1013 default:
1014 i+=3;
1015 sPart += c;
1016 sPart += c;
1017 sPart += c;
1018 break;
1019 }
1020 }
1021 else if (format.GetAt(i+1) == c && format.GetAt(i+2) == c && format.GetAt(i+3) == c && format.GetAt(i+4) != c)
1022 {
1023 switch (c)
1024 {
1025 case 'y':
1026 sPart.Format((FX_LPCWSTR)L"%04d",nYear);
1027 i += 4;
1028 break;
1029 case 'm':
1030 i+=4;
1031 if (nMonth > 0&&nMonth <= 12)
1032 sPart += fullmonths[nMonth - 1];
1033 break;
1034 default:
1035 i += 4;
1036 sPart += c;
1037 sPart += c;
1038 sPart += c;
1039 sPart += c;
1040 break;
1041 }
1042 }
1043 else
1044 {
1045 i++;
1046 sPart += c;
1047 }
1048 break;
1049 default:
1050 i++;
1051 sPart += c;
1052 break;
1053 }
1054
1055 sRet += sPart;
1056 }
1057
1058 return sRet;
1059}
1060
1061/* -------------------------------------------------------------------------- */
1062
1063//function AFNumber_Format(nDec, sepStyle, negStyle, currStyle, strCurrency, bCurrencyPrepend)
1064FX_BOOL CJS_PublicMethods::AFNumber_Format(OBJ_METHOD_PARAMS)
1065{
1066#if _FX_OS_ != _FX_ANDROID_
1067 v8::Isolate* isolate = ::GetIsolate(cc);
1068 CJS_Context* pContext = (CJS_Context *)cc;
1069 ASSERT(pContext != NULL);
1070 CJS_EventHandler* pEvent = pContext->GetEventHandler();
1071 ASSERT(pEvent != NULL);
1072
1073 if (params.size() != 6)
1074 {
1075 sError = JSGetStringFromID(pContext, IDS_STRING_JSPARAMERROR);
1076 return FALSE;
1077 }
1078 if(!pEvent->m_pValue)
1079 return FALSE;
1080 CFX_WideString& Value = pEvent->Value();
1081 CFX_ByteString strValue = StrTrim(CFX_ByteString::FromUnicode(Value));
1082
1083 if (strValue.IsEmpty()) return TRUE;
1084
1085 int iDec = params[0];
1086 int iSepStyle = params[1];
1087 int iNegStyle = params[2];
1088 int icurrStyle = params[3]; //it's no use!
1089 std::wstring wstrCurrency(params[4].operator CFX_WideString());
1090 FX_BOOL bCurrencyPrepend = params[5];
1091
1092 if (iDec < 0) iDec = -iDec;
1093
1094 if (iSepStyle < 0 || iSepStyle > 3)
1095 iSepStyle = 0;
1096
1097 if (iNegStyle < 0 || iNegStyle > 3)
1098 iNegStyle = 0;
1099
1100
1101 //////////////////////////////////////////////////////
1102 //for processing decimal places
1103 strValue.Replace(",", ".");
1104 double dValue = atof(strValue);
1105 if (iDec > 0)
1106 dValue += DOUBLE_CORRECT;//
1107
1108 int iDec2;
1109 FX_BOOL bNagative = FALSE;
1110
1111 strValue = fcvt(dValue,iDec,&iDec2,&bNagative);
1112 if (strValue.IsEmpty())
1113 {
1114 dValue = 0;
1115 strValue = fcvt(dValue,iDec,&iDec2,&bNagative);
1116 if (strValue.IsEmpty())
1117 {
1118 strValue = "0";
1119 iDec2 = 1;
1120 }
1121
1122 }
1123
1124 if (iDec2 < 0)
1125 {
1126 for (int iNum = 0;iNum < abs(iDec2);iNum++)
1127 {
1128 strValue = "0" + strValue;
1129 }
1130 iDec2 = 0;
1131
1132 }
1133 int iMax = strValue.GetLength();
1134 if (iDec2 > iMax)
1135 {
1136 for (int iNum = 0;iNum <= iDec2 - iMax ;iNum++)
1137 {
1138 strValue += "0";
1139 }
1140 iMax = iDec2+1;
1141 }
1142 ///////////////////////////////////////////////////////
1143 //for processing seperator style
1144 if (iDec2 < iMax)
1145 {
1146 if (iSepStyle == 0 || iSepStyle == 1)
1147 {
1148 strValue.Insert(iDec2, '.');
1149 iMax++;
1150 }
1151 else if (iSepStyle == 2 || iSepStyle == 3)
1152 {
1153 strValue.Insert(iDec2, ',');
1154 iMax++;
1155 }
1156
1157 if (iDec2 == 0)
1158 strValue.Insert(iDec2, '0');
1159 }
1160 if (iSepStyle == 0 || iSepStyle == 2)
1161 {
1162 char cSeperator;
1163 if (iSepStyle == 0)
1164 cSeperator = ',';
1165 else
1166 cSeperator = '.';
1167
1168 int iDecPositive,iDecNagative;
1169 iDecPositive = iDec2;
1170 iDecNagative = iDec2;
1171
1172 for (iDecPositive = iDec2 -3; iDecPositive > 0;iDecPositive -= 3)
1173 {
1174 strValue.Insert(iDecPositive, cSeperator);
1175 iMax++;
1176 }
1177 }
1178
1179 //////////////////////////////////////////////////////////////////////
1180 //for processing currency string
1181
1182 Value = CFX_WideString::FromLocal(strValue);
1183
1184 std::wstring strValue2(Value);
1185
1186 if (bCurrencyPrepend)
1187 strValue2 = wstrCurrency + strValue2;
1188 else
1189 strValue2 = strValue2 + wstrCurrency;
1190
1191
1192
1193 /////////////////////////////////////////////////////////////////////////
1194 //for processing negative style
1195 if (bNagative)
1196 {
1197 if (iNegStyle == 0)
1198 {
1199 strValue2.insert(0,L"-");
1200 }
1201 if (iNegStyle == 2 || iNegStyle == 3)
1202 {
1203 strValue2.insert(0,L"(");
1204 strValue2.insert(strValue2.length(),L")");
1205 }
1206 if (iNegStyle == 1 || iNegStyle == 3)
1207 {
1208 if (Field * fTarget = pEvent->Target_Field())
1209 {
1210 CJS_Array arColor(isolate);
1211 CJS_Value vColElm(isolate);
1212 vColElm = L"RGB";
1213 arColor.SetElement(0,vColElm);
1214 vColElm = 1;
1215 arColor.SetElement(1,vColElm);
1216 vColElm = 0;
1217 arColor.SetElement(2,vColElm);
1218
1219 arColor.SetElement(3,vColElm);
1220
1221 CJS_PropValue vProp(isolate);
1222 vProp.StartGetting();
1223 vProp<<arColor;
1224 vProp.StartSetting();
1225 fTarget->textColor(cc,vProp,sError);// red
1226 }
1227 }
1228 }
1229 else
1230 {
1231 if (iNegStyle == 1 || iNegStyle == 3)
1232 {
1233 if (Field *fTarget = pEvent->Target_Field())
1234 {
1235 CJS_Array arColor(isolate);
1236 CJS_Value vColElm(isolate);
1237 vColElm = L"RGB";
1238 arColor.SetElement(0,vColElm);
1239 vColElm = 0;
1240 arColor.SetElement(1,vColElm);
1241 arColor.SetElement(2,vColElm);
1242 arColor.SetElement(3,vColElm);
1243
1244 CJS_PropValue vProp(isolate);
1245 vProp.StartGetting();
1246 fTarget->textColor(cc,vProp,sError);
1247
1248 CJS_Array aProp(isolate);
1249 vProp.ConvertToArray(aProp);
1250
1251 CPWL_Color crProp;
1252 CPWL_Color crColor;
1253 color::ConvertArrayToPWLColor(aProp, crProp);
1254 color::ConvertArrayToPWLColor(arColor, crColor);
1255
1256 if (crColor != crProp)
1257 {
1258 CJS_PropValue vProp2(isolate);
1259 vProp2.StartGetting();
1260 vProp2<<arColor;
1261 vProp2.StartSetting();
1262 fTarget->textColor(cc,vProp2,sError);
1263 }
1264 }
1265 }
1266 }
1267 Value = strValue2.c_str();
1268#endif
1269 return TRUE;
1270}
1271
1272//function AFNumber_Keystroke(nDec, sepStyle, negStyle, currStyle, strCurrency, bCurrencyPrepend)
1273FX_BOOL CJS_PublicMethods::AFNumber_Keystroke(OBJ_METHOD_PARAMS)
1274{
1275 CJS_Context* pContext = (CJS_Context *)cc;
1276 ASSERT(pContext != NULL);
1277 CJS_EventHandler* pEvent = pContext->GetEventHandler();
1278 ASSERT(pEvent != NULL);
1279
1280 if(params.size() < 2)
1281 return FALSE;
1282 int iSepStyle = params[1];
1283
1284 if (iSepStyle < 0 || iSepStyle > 3)
1285 iSepStyle = 0;
1286 if(!pEvent->m_pValue)
1287 return FALSE;
1288 CFX_WideString & val = pEvent->Value();
1289 CFX_WideString & w_strChange = pEvent->Change();
1290 CFX_WideString w_strValue = val;
1291
1292 if (pEvent->WillCommit())
1293 {
1294 CFX_WideString wstrChange = w_strChange;
1295 CFX_WideString wstrValue = StrLTrim(w_strValue);
1296 if (wstrValue.IsEmpty())
1297 return TRUE;
1298
1299 CFX_WideString swTemp = wstrValue;
1300 swTemp.Replace((FX_LPCWSTR)L",", (FX_LPCWSTR)L".");
1301 if (!IsNumber(swTemp)) //!(IsNumber(wstrChange) &&
1302 {
1303 pEvent->Rc() = FALSE;
1304 sError = JSGetStringFromID(pContext, IDS_STRING_JSAFNUMBER_KEYSTROKE);
1305 Alert(pContext, sError);
1306 return TRUE;
1307 }
1308 return TRUE; // it happens after the last keystroke and before validating,
1309 }
1310
1311 std::wstring w_strValue2 (w_strValue);
1312 std::wstring w_strChange2(w_strChange);
1313
1314 std::wstring w_strSelected;
1315 if(-1 != pEvent->SelStart())
1316 w_strSelected = w_strValue2.substr(pEvent->SelStart(),(pEvent->SelEnd() - pEvent->SelStart()));
1317 FX_BOOL bHasSign = (w_strValue2.find('-') != -1) && (w_strSelected.find('-') == -1);
1318 if (bHasSign)
1319 {
1320 //can't insert "change" in front to sign postion.
1321 if (pEvent->SelStart() == 0)
1322 {
1323 FX_BOOL &bRc = pEvent->Rc();
1324 bRc = FALSE;
1325 return TRUE;
1326 }
1327 }
1328
1329 char cSep = L'.';
1330
1331 switch (iSepStyle)
1332 {
1333 case 0:
1334 case 1:
1335 cSep = L'.';
1336 break;
1337 case 2:
1338 case 3:
1339 cSep = L',';
1340 break;
1341 }
1342
1343 FX_BOOL bHasSep = (w_strValue2.find(cSep) != -1);
1344 for (std::wstring::iterator it = w_strChange2.begin(); it != w_strChange2.end(); it++)
1345 {
1346 if (*it == cSep)
1347 {
1348 if (bHasSep)
1349 {
1350 FX_BOOL &bRc = pEvent->Rc();
1351 bRc = FALSE;
1352 return TRUE;
1353 }
1354 else
1355 {
1356 bHasSep = TRUE;
1357 continue;
1358 }
1359 }
1360 if (*it == L'-')
1361 {
1362 if (bHasSign)
1363 {
1364 FX_BOOL &bRc = pEvent->Rc();
1365 bRc = FALSE;
1366 return TRUE;
1367 }
1368 else if (it != w_strChange2.begin()) //sign's position is not correct
1369 {
1370 FX_BOOL &bRc = pEvent->Rc();
1371 bRc = FALSE;
1372 return TRUE;
1373 }
1374 else if (pEvent->SelStart() != 0)
1375 {
1376 FX_BOOL &bRc = pEvent->Rc();
1377 bRc = FALSE;
1378 return TRUE;
1379 }
1380 bHasSign = TRUE;
1381 continue;
1382 }
1383
1384 if (!IsDigit(*it))
1385 {
1386 FX_BOOL &bRc = pEvent->Rc();
1387 bRc = FALSE;
1388 return TRUE;
1389 }
1390 }
1391
1392
1393 std::wstring w_prefix = w_strValue2.substr(0,pEvent->SelStart());
1394 std::wstring w_postfix;
1395 if (pEvent->SelEnd()<(int)w_strValue2.length())
1396 w_postfix = w_strValue2.substr(pEvent->SelEnd());
1397 w_strValue2 = w_prefix + w_strChange2 + w_postfix;
1398 w_strValue = w_strValue2.c_str();
1399 val = w_strValue;
1400 return TRUE;
1401
1402}
1403
1404//function AFPercent_Format(nDec, sepStyle)
1405FX_BOOL CJS_PublicMethods::AFPercent_Format(OBJ_METHOD_PARAMS)
1406{
1407#if _FX_OS_ != _FX_ANDROID_
1408 CJS_Context* pContext = (CJS_Context *)cc;
1409 ASSERT(pContext != NULL);
1410 CJS_EventHandler* pEvent = pContext->GetEventHandler();
1411 ASSERT(pEvent != NULL);
1412
1413 if (params.size() != 2)
1414 {
1415 sError = JSGetStringFromID(pContext, IDS_STRING_JSPARAMERROR);
1416 return FALSE;
1417 }
1418 if(!pEvent->m_pValue)
1419 return FALSE;
1420 CFX_WideString& Value = pEvent->Value();
1421
1422// HWND hMainFrame = NULL;
1423//
1424// CPDFSDK_FormFillApp *pApp = pContext->GetReaderApp();
1425// ASSERT(pApp);
1426// hMainFrame = pApp->GetMainFrameWnd();
1427
1428 CFX_ByteString strValue = StrTrim(CFX_ByteString::FromUnicode(Value));
1429
1430 if (strValue.IsEmpty())
1431 return TRUE;
1432
1433 int iDec = params[0];
1434 int iSepStyle = params[1];
1435
1436 //ASSERT(iDec > 0);
1437 if (iDec < 0)
1438 iDec = -iDec;
1439
1440 if (iSepStyle < 0 || iSepStyle > 3)
1441 iSepStyle = 0;
1442
1443
1444 //////////////////////////////////////////////////////
1445 //for processing decimal places
1446 double dValue = atof(strValue);
1447 dValue *= 100;
1448 if (iDec > 0)
1449 dValue += DOUBLE_CORRECT;//УÕý
1450
1451 int iDec2;
1452 FX_BOOL bNagative = FALSE;
1453 strValue = fcvt(dValue,iDec,&iDec2,&bNagative);
1454 if (strValue.IsEmpty())
1455 {
1456 dValue = 0;
1457 strValue = fcvt(dValue,iDec,&iDec2,&bNagative);
1458 }
1459
1460 if (iDec2 < 0)
1461 {
1462 for (int iNum = 0; iNum < abs(iDec2); iNum++)
1463 {
1464 strValue = "0" + strValue;
1465 }
1466 iDec2 = 0;
1467
1468 }
1469 int iMax = strValue.GetLength();
1470 if (iDec2 > iMax)
1471 {
1472 for (int iNum = 0; iNum <= iDec2 - iMax; iNum++)
1473 {
1474 strValue += "0";
1475 }
1476 iMax = iDec2+1;
1477 }
1478 ///////////////////////////////////////////////////////
1479 //for processing seperator style
1480 if (iDec2 < iMax)
1481 {
1482 if (iSepStyle == 0 || iSepStyle == 1)
1483 {
1484 strValue.Insert(iDec2, '.');
1485 iMax++;
1486 }
1487 else if (iSepStyle == 2 || iSepStyle == 3)
1488 {
1489 strValue.Insert(iDec2, ',');
1490 iMax++;
1491 }
1492
1493 if (iDec2 == 0)
1494 strValue.Insert(iDec2, '0');
1495 }
1496 if (iSepStyle == 0 || iSepStyle == 2)
1497 {
1498 char cSeperator;
1499 if (iSepStyle == 0)
1500 cSeperator = ',';
1501 else
1502 cSeperator = '.';
1503
1504 int iDecPositive,iDecNagative;
1505 iDecPositive = iDec2;
1506 iDecNagative = iDec2;
1507
1508 for (iDecPositive = iDec2 -3; iDecPositive > 0; iDecPositive -= 3)
1509 {
1510 strValue.Insert(iDecPositive,cSeperator);
1511 iMax++;
1512 }
1513 }
1514 ////////////////////////////////////////////////////////////////////
1515 //nagative mark
1516 if(bNagative)
1517 strValue = "-" + strValue;
1518 strValue += "%";
1519 Value = CFX_WideString::FromLocal(strValue);
1520#endif
1521 return TRUE;
1522}
1523//AFPercent_Keystroke(nDec, sepStyle)
1524FX_BOOL CJS_PublicMethods::AFPercent_Keystroke(OBJ_METHOD_PARAMS)
1525{
1526 return AFNumber_Keystroke(cc,params,vRet,sError);
1527}
1528
1529//function AFDate_FormatEx(cFormat)
1530FX_BOOL CJS_PublicMethods::AFDate_FormatEx(OBJ_METHOD_PARAMS)
1531{
1532 CJS_Context* pContext = (CJS_Context *)cc;
1533 ASSERT(pContext != NULL);
1534 CJS_EventHandler* pEvent = pContext->GetEventHandler();
1535 ASSERT(pEvent != NULL);
1536
1537 if (params.size() != 1)
1538 {
1539 sError = JSGetStringFromID(pContext, IDS_STRING_JSPARAMERROR);
1540 return FALSE;
1541 }
1542 if(!pEvent->m_pValue)
1543 return FALSE;
1544 CFX_WideString& val = pEvent->Value();
1545
1546 CFX_WideString strValue = val;
1547 if (strValue.IsEmpty()) return TRUE;
1548
1549 CFX_WideString sFormat = params[0].operator CFX_WideString();
1550
1551 FX_BOOL bWrongFormat = FALSE;
1552 double dDate = 0.0f;
1553
1554 if(strValue.Find(L"GMT") != -1)
1555 {
1556 //for GMT format time
1557 //such as "Tue Aug 11 14:24:16 GMT+08002009"
1558 dDate = MakeInterDate(strValue);
1559 }
1560 else
1561 {
1562 dDate = MakeRegularDate(strValue,sFormat,bWrongFormat);
1563 }
1564
1565 if (JS_PortIsNan(dDate))
1566 {
1567 CFX_WideString swMsg;
1568 swMsg.Format(JSGetStringFromID(pContext, IDS_STRING_JSPARSEDATE), (FX_LPCWSTR)sFormat);
1569 Alert(pContext, swMsg);
1570 return FALSE;
1571 }
1572
1573 val = MakeFormatDate(dDate,sFormat);
1574
1575 return TRUE;
1576}
1577
1578double CJS_PublicMethods::MakeInterDate(CFX_WideString strValue)
1579{
1580 int nHour;
1581 int nMin;
1582 int nSec;
1583 int nYear;
1584 int nMonth;
1585 int nDay;
1586
1587 CFX_WideStringArray wsArray;
1588 CFX_WideString sMonth = L"";
1589 CFX_WideString sTemp = L"";
1590 int nSize = strValue.GetLength();
1591
1592 for(int i = 0; i < nSize; i++)
1593 {
1594 FX_WCHAR c = strValue.GetAt(i);
1595 if(c == L' ' || c == L':')
1596 {
1597 wsArray.Add(sTemp);
1598 sTemp = L"";
1599 continue;
1600 }
1601
1602 sTemp += c;
1603 }
1604
1605 wsArray.Add(sTemp);
1606 if(wsArray.GetSize() != 8)return 0;
1607
1608 sTemp = wsArray[1];
1609 if(sTemp.Compare(L"Jan") == 0) nMonth = 1;
1610 if(sTemp.Compare(L"Feb") == 0) nMonth = 2;
1611 if(sTemp.Compare(L"Mar") == 0) nMonth = 3;
1612 if(sTemp.Compare(L"Apr") == 0) nMonth = 4;
1613 if(sTemp.Compare(L"May") == 0) nMonth = 5;
1614 if(sTemp.Compare(L"Jun") == 0) nMonth = 6;
1615 if(sTemp.Compare(L"Jul") == 0) nMonth = 7;
1616 if(sTemp.Compare(L"Aug") == 0) nMonth = 8;
1617 if(sTemp.Compare(L"Sep") == 0) nMonth = 9;
1618 if(sTemp.Compare(L"Oct") == 0) nMonth = 10;
1619 if(sTemp.Compare(L"Nov") == 0) nMonth = 11;
1620 if(sTemp.Compare(L"Dec") == 0) nMonth = 12;
1621
1622 nDay = (int)ParseStringToNumber(wsArray[2]);
1623 nHour = (int)ParseStringToNumber(wsArray[3]);
1624 nMin = (int)ParseStringToNumber(wsArray[4]);
1625 nSec = (int)ParseStringToNumber(wsArray[5]);
1626 nYear = (int)ParseStringToNumber(wsArray[7]);
1627
1628 double dRet = JS_MakeDate(JS_MakeDay(nYear,nMonth - 1,nDay),JS_MakeTime(nHour, nMin, nSec, 0));
1629
1630 if (JS_PortIsNan(dRet))
1631 {
1632 dRet = JS_DateParse(strValue);
1633 }
1634
1635 return dRet;
1636}
1637
1638//AFDate_KeystrokeEx(cFormat)
1639FX_BOOL CJS_PublicMethods::AFDate_KeystrokeEx(OBJ_METHOD_PARAMS)
1640{
1641 CJS_Context* pContext = (CJS_Context *)cc;
1642 ASSERT(pContext != NULL);
1643 CJS_EventHandler* pEvent = pContext->GetEventHandler();
1644 ASSERT(pEvent != NULL);
1645
1646 if (params.size() != 1)
1647 {
1648 sError = L"AFDate_KeystrokeEx's parameters' size r not correct";
1649 return FALSE;
1650 }
1651
1652 if (pEvent->WillCommit())
1653 {
1654 if(!pEvent->m_pValue)
1655 return FALSE;
1656 CFX_WideString strValue = pEvent->Value();
1657 if (strValue.IsEmpty()) return TRUE;
1658
1659 CFX_WideString sFormat = params[0].operator CFX_WideString();
1660
1661 FX_BOOL bWrongFormat = FALSE;
1662 double dRet = MakeRegularDate(strValue,sFormat,bWrongFormat);
1663 if (bWrongFormat || JS_PortIsNan(dRet))
1664 {
1665 CFX_WideString swMsg;
1666 swMsg.Format(JSGetStringFromID(pContext, IDS_STRING_JSPARSEDATE), (FX_LPCWSTR)sFormat);
1667 Alert(pContext, swMsg);
1668 pEvent->Rc() = FALSE;
1669 return TRUE;
1670 }
1671 }
1672 return TRUE;
1673}
1674
1675FX_BOOL CJS_PublicMethods::AFDate_Format(OBJ_METHOD_PARAMS)
1676{
1677 v8::Isolate* isolate = ::GetIsolate(cc);
1678
1679 if (params.size() != 1)
1680 {
1681 CJS_Context* pContext = (CJS_Context*)cc;
1682 ASSERT(pContext != NULL);
1683
1684 sError = JSGetStringFromID(pContext, IDS_STRING_JSPARAMERROR);
1685 return FALSE;
1686 }
1687
1688 int iIndex = params[0];
1689 FX_LPCWSTR cFormats[] = {(FX_LPCWSTR)L"m/d", (FX_LPCWSTR)L"m/d/yy", (FX_LPCWSTR)L"mm/dd/yy", (FX_LPCWSTR)L"mm/yy", (FX_LPCWSTR)L"d-mmm", (FX_LPCWSTR)L"d-mmm-yy", (FX_LPCWSTR)L"dd-mmm-yy",
1690 (FX_LPCWSTR)L"yy-mm-dd", (FX_LPCWSTR)L"mmm-yy", (FX_LPCWSTR)L"mmmm-yy", (FX_LPCWSTR)L"mmm d, yyyy", (FX_LPCWSTR)L"mmmm d, yyyy",
1691 (FX_LPCWSTR)L"m/d/yy h:MM tt", (FX_LPCWSTR)L"m/d/yy HH:MM" };
1692
1693 ASSERT(iIndex < sizeof(cFormats)/sizeof(FX_LPCWSTR));
1694
1695 if (iIndex < 0)
1696 iIndex = 0;
1697 if (iIndex >= sizeof(cFormats)/sizeof(FX_LPCWSTR))
1698 iIndex = 0;
1699 CJS_Parameters newParams;
1700 CJS_Value val(isolate,cFormats[iIndex]);
1701 newParams.push_back(val);
1702 return AFDate_FormatEx(cc,newParams,vRet,sError);
1703}
1704
1705//AFDate_KeystrokeEx(cFormat)
1706FX_BOOL CJS_PublicMethods::AFDate_Keystroke(OBJ_METHOD_PARAMS)
1707{
1708 v8::Isolate* isolate = ::GetIsolate(cc);
1709
1710 if (params.size() != 1)
1711 {
1712 CJS_Context* pContext = (CJS_Context*)cc;
1713 ASSERT(pContext != NULL);
1714
1715 sError = JSGetStringFromID(pContext, IDS_STRING_JSPARAMERROR);
1716 return FALSE;
1717 }
1718
1719 int iIndex = params[0];
1720 FX_LPCWSTR cFormats[] = {(FX_LPCWSTR)L"m/d", (FX_LPCWSTR)L"m/d/yy", (FX_LPCWSTR)L"mm/dd/yy", (FX_LPCWSTR)L"mm/yy", (FX_LPCWSTR)L"d-mmm", (FX_LPCWSTR)L"d-mmm-yy", (FX_LPCWSTR)L"dd-mmm-yy",
1721 (FX_LPCWSTR)L"yy-mm-dd", (FX_LPCWSTR)L"mmm-yy", (FX_LPCWSTR)L"mmmm-yy", (FX_LPCWSTR)L"mmm d, yyyy", (FX_LPCWSTR)L"mmmm d, yyyy",
1722 (FX_LPCWSTR)L"m/d/yy h:MM tt", (FX_LPCWSTR)L"m/d/yy HH:MM" };
1723
1724 ASSERT(iIndex<sizeof(cFormats)/sizeof(FX_LPCWSTR));
1725
1726 if (iIndex < 0)
1727 iIndex = 0;
1728 if (iIndex >= sizeof(cFormats)/sizeof(FX_LPCWSTR))
1729 iIndex = 0;
1730 CJS_Parameters newParams;
1731 CJS_Value val(isolate,cFormats[iIndex]);
1732 newParams.push_back(val);
1733 return AFDate_KeystrokeEx(cc,newParams,vRet,sError);
1734}
1735
1736//function AFTime_Format(ptf)
1737FX_BOOL CJS_PublicMethods::AFTime_Format(OBJ_METHOD_PARAMS)
1738{
1739 v8::Isolate* isolate = ::GetIsolate(cc);
1740
1741 if (params.size() != 1)
1742 {
1743 CJS_Context* pContext = (CJS_Context*)cc;
1744 ASSERT(pContext != NULL);
1745 sError = JSGetStringFromID(pContext, IDS_STRING_JSPARAMERROR);
1746 return FALSE;
1747 }
1748
1749 int iIndex = params[0];
1750 FX_LPCWSTR cFormats[] = {(FX_LPCWSTR)L"HH:MM", (FX_LPCWSTR)L"h:MM tt", (FX_LPCWSTR)L"HH:MM:ss", (FX_LPCWSTR)L"h:MM:ss tt"};
1751
1752 ASSERT(iIndex<sizeof(cFormats)/sizeof(FX_LPCWSTR));
1753
1754 if (iIndex < 0)
1755 iIndex = 0;
1756 if (iIndex >= sizeof(cFormats)/sizeof(FX_LPCWSTR))
1757 iIndex = 0;
1758 CJS_Parameters newParams;
1759 CJS_Value val(isolate,cFormats[iIndex]);
1760 newParams.push_back(val);
1761 return AFDate_FormatEx(cc,newParams,vRet,sError);
1762}
1763
1764FX_BOOL CJS_PublicMethods::AFTime_Keystroke(OBJ_METHOD_PARAMS)
1765{
1766 v8::Isolate* isolate = ::GetIsolate(cc);
1767 if (params.size() != 1)
1768 {
1769 CJS_Context* pContext = (CJS_Context*)cc;
1770 ASSERT(pContext != NULL);
1771 sError = JSGetStringFromID(pContext, IDS_STRING_JSPARAMERROR);
1772 return FALSE;
1773 }
1774
1775 int iIndex = params[0];
1776 FX_LPCWSTR cFormats[] = {(FX_LPCWSTR)L"HH:MM", (FX_LPCWSTR)L"h:MM tt", (FX_LPCWSTR)L"HH:MM:ss", (FX_LPCWSTR)L"h:MM:ss tt"};
1777
1778 ASSERT(iIndex<sizeof(cFormats)/sizeof(FX_LPCWSTR));
1779
1780 if (iIndex < 0)
1781 iIndex = 0;
1782 if (iIndex >= sizeof(cFormats)/sizeof(FX_LPCWSTR))
1783 iIndex = 0;
1784 CJS_Parameters newParams;
1785 CJS_Value val(isolate,cFormats[iIndex]);
1786 newParams.push_back(val);
1787 return AFDate_KeystrokeEx(cc,newParams,vRet,sError);
1788}
1789
1790FX_BOOL CJS_PublicMethods::AFTime_FormatEx(OBJ_METHOD_PARAMS)
1791{
1792 return AFDate_FormatEx(cc,params,vRet,sError);
1793}
1794
1795FX_BOOL CJS_PublicMethods::AFTime_KeystrokeEx(OBJ_METHOD_PARAMS)
1796{
1797 return AFDate_KeystrokeEx(cc,params,vRet,sError);
1798}
1799
1800//function AFSpecial_Format(psf)
1801FX_BOOL CJS_PublicMethods::AFSpecial_Format(OBJ_METHOD_PARAMS)
1802{
1803 CJS_Context* pContext = (CJS_Context *)cc;
1804 ASSERT(pContext != NULL);
1805
1806 if (params.size() != 1)
1807 {
1808 sError = JSGetStringFromID(pContext, IDS_STRING_JSPARAMERROR);
1809 return FALSE;
1810 }
1811
1812 std::string cFormat;
1813 int iIndex = params[0];
1814
1815 CJS_EventHandler* pEvent = pContext->GetEventHandler();
1816 ASSERT(pEvent != NULL);
1817
1818 if(!pEvent->m_pValue)
1819 return FALSE;
1820 CFX_WideString& Value = pEvent->Value();
1821 std::string strSrc = (FX_LPCSTR)CFX_ByteString::FromUnicode(Value);
1822
1823 switch (iIndex)
1824 {
1825 case 0:
1826 cFormat = "99999";
1827 break;
1828 case 1:
1829 cFormat = "99999-9999";
1830 break;
1831 case 2:
1832 {
1833 std::string NumberStr;
1834 util::printx("9999999999", strSrc,NumberStr);
1835 if (NumberStr.length() >= 10 )
1836 cFormat = "(999) 999-9999";
1837 else
1838 cFormat = "999-9999";
1839 break;
1840 }
1841 case 3:
1842 cFormat = "999-99-9999";
1843 break;
1844 }
1845
1846 std::string strDes;
1847 util::printx(cFormat,strSrc,strDes);
1848 Value = CFX_WideString::FromLocal(strDes.c_str());
1849 return TRUE;
1850}
1851
1852
1853//function AFSpecial_KeystrokeEx(mask)
1854FX_BOOL CJS_PublicMethods::AFSpecial_KeystrokeEx(OBJ_METHOD_PARAMS)
1855{
1856 CJS_Context* pContext = (CJS_Context *)cc;
1857 ASSERT(pContext != NULL);
1858 CJS_EventHandler* pEvent = pContext->GetEventHandler();
1859
1860 ASSERT(pEvent != NULL);
1861
1862 if (params.size() < 1)
1863 {
1864 sError = JSGetStringFromID(pContext, IDS_STRING_JSPARAMERROR);
1865 return FALSE;
1866 }
1867
1868 if(!pEvent->m_pValue)
1869 return FALSE;
1870 CFX_WideString& valEvent = pEvent->Value();
1871
1872 CFX_WideString wstrMask = params[0].operator CFX_WideString();
1873 if (wstrMask.IsEmpty()) return TRUE;
1874
1875 std::wstring wstrValue(valEvent);
1876
1877 if (pEvent->WillCommit())
1878 {
1879 if (wstrValue.empty())
1880 return TRUE;
1881 int iIndexMask = 0;
1882 for (std::wstring::iterator it = wstrValue.begin(); it != wstrValue.end(); it++)
1883 {
1884 wchar_t w_Value = *it;
1885 if (!maskSatisfied(w_Value,wstrMask[iIndexMask]))
1886 break;
1887 iIndexMask++;
1888 }
1889
1890 if (iIndexMask != wstrMask.GetLength() || (iIndexMask != wstrValue.size() && wstrMask.GetLength() != 0))
1891 {
1892 Alert(pContext, JSGetStringFromID(pContext, IDS_STRING_JSAFNUMBER_KEYSTROKE));
1893 pEvent->Rc() = FALSE;
1894 }
1895 return TRUE;
1896 }
1897
1898
1899 CFX_WideString &wideChange = pEvent->Change();
1900 std::wstring wChange(wideChange);
1901
1902 if (wChange.empty())
1903 return TRUE;
1904 int iIndexMask = pEvent->SelStart();
1905 //iIndexMask++;
1906
1907
1908 if (wstrValue.length() - (pEvent->SelEnd()-pEvent->SelStart()) + wChange.length() > (FX_DWORD)wstrMask.GetLength())
1909 {
1910 Alert(pContext, JSGetStringFromID(pContext, IDS_STRING_JSPARAM_TOOLONG));
1911 pEvent->Rc() = FALSE;
1912 return TRUE;
1913 }
1914
1915
1916 if (iIndexMask >= wstrMask.GetLength() && (!wChange.empty()))
1917 {
1918 Alert(pContext, JSGetStringFromID(pContext, IDS_STRING_JSPARAM_TOOLONG));
1919 pEvent->Rc() = FALSE;
1920 return TRUE;
1921 }
1922
1923 for (std::wstring::iterator it = wChange.begin(); it != wChange.end(); it++)
1924 {
1925 if (iIndexMask >= wstrMask.GetLength())
1926 {
1927 Alert(pContext, JSGetStringFromID(pContext, IDS_STRING_JSPARAM_TOOLONG));
1928 pEvent->Rc() = FALSE;
1929 return TRUE;
1930 }
1931 wchar_t w_Mask = wstrMask[iIndexMask];
1932 if (!isReservedMaskChar(w_Mask))
1933 {
1934 //wChange.insert(it,w_Mask);
1935 *it = w_Mask;
1936 }
1937 wchar_t w_Change = *it;
1938
1939 if (!maskSatisfied(w_Change,w_Mask))
1940 {
1941 pEvent->Rc() = FALSE;
1942 return TRUE;
1943 }
1944 iIndexMask++;
1945 }
1946
1947 wideChange = wChange.c_str();
1948
1949 return TRUE;
1950}
1951
1952
1953//function AFSpecial_Keystroke(psf)
1954FX_BOOL CJS_PublicMethods::AFSpecial_Keystroke(OBJ_METHOD_PARAMS)
1955{
1956 v8::Isolate* isolate = ::GetIsolate(cc);
1957
1958 CJS_Context* pContext = (CJS_Context *)cc;
1959 ASSERT(pContext != NULL);
1960 CJS_EventHandler* pEvent = pContext->GetEventHandler();
1961 ASSERT(pEvent != NULL);
1962
1963 if (params.size() != 1)
1964 {
1965 sError = JSGetStringFromID(pContext, IDS_STRING_JSPARAMERROR);
1966 return FALSE;
1967 }
1968
1969 std::string cFormat;
1970 int iIndex = (int)params[0];
1971
1972 if(!pEvent->m_pValue)
1973 return FALSE;
1974 //CJS_Value val = pEvent->Value();
1975 CFX_WideString& val = pEvent->Value();
1976 std::string strSrc = (FX_LPCSTR)CFX_ByteString::FromUnicode(val);
1977 std::wstring wstrChange(pEvent->Change());
1978
1979 switch (iIndex)
1980 {
1981 case 0:
1982 cFormat = "99999";
1983 break;
1984 case 1:
1985 //cFormat = "99999-9999";
1986 cFormat = "999999999";
1987 break;
1988 case 2:
1989 {
1990 std::string NumberStr;
1991 util::printx("9999999999", strSrc,NumberStr);
1992 if (strSrc.length() + wstrChange.length() > 7 )
1993 //cFormat = "(999) 999-9999";
1994 cFormat = "9999999999";
1995 else
1996 //cFormat = "999-9999";
1997 cFormat = "9999999";
1998 break;
1999 }
2000 case 3:
2001 //cFormat = "999-99-9999";
2002 cFormat = "999999999";
2003 break;
2004 }
2005
2006 CJS_Parameters params2;
2007 CJS_Value vMask(isolate, cFormat.c_str());
2008 params2.push_back(vMask);
2009
2010 return AFSpecial_KeystrokeEx(cc,params2,vRet,sError);
2011}
2012
2013FX_BOOL CJS_PublicMethods::AFMergeChange(OBJ_METHOD_PARAMS)
2014{
2015 CJS_Context* pContext = (CJS_Context *)cc;
2016 ASSERT(pContext != NULL);
2017 CJS_EventHandler* pEventHandler = pContext->GetEventHandler();
2018 ASSERT(pEventHandler != NULL);
2019
2020 if (params.size() != 1)
2021 {
2022 sError = JSGetStringFromID(pContext, IDS_STRING_JSPARAMERROR);
2023 return FALSE;
2024 }
2025
2026 CFX_WideString swValue;
2027 if (pEventHandler->m_pValue != NULL)
2028 swValue = pEventHandler->Value();
2029
2030 if (pEventHandler->WillCommit())
2031 {
2032 vRet = swValue;
2033 return TRUE;
2034 }
2035
2036 CFX_WideString prefix,postfix;
2037
2038 if (pEventHandler->SelStart() >= 0)
2039 prefix = swValue.Mid(0,pEventHandler->SelStart());
2040 else
2041 prefix = L"";
2042
2043
2044 if (pEventHandler->SelEnd() >= 0 && pEventHandler->SelEnd() <= swValue.GetLength())
2045 postfix = swValue.Mid(pEventHandler->SelEnd(), swValue.GetLength() - pEventHandler->SelEnd());
2046 else postfix = L"";
2047
2048 vRet = prefix + pEventHandler->Change() + postfix;
2049
2050 return TRUE;
2051}
2052
2053FX_BOOL CJS_PublicMethods::AFParseDateEx(OBJ_METHOD_PARAMS)
2054{
2055 CJS_Context* pContext = (CJS_Context *)cc;
2056 ASSERT(pContext != NULL);
2057
2058 if (params.size() != 2)
2059 {
2060 sError = JSGetStringFromID(pContext, IDS_STRING_JSPARAMERROR);
2061 return FALSE;
2062 }
2063
2064 CFX_WideString sValue = params[0].operator CFX_WideString();
2065 CFX_WideString sFormat = params[1].operator CFX_WideString();
2066
2067 FX_BOOL bWrongFormat = FALSE;
2068 double dDate = MakeRegularDate(sValue,sFormat,bWrongFormat);
2069
2070 if (JS_PortIsNan(dDate))
2071 {
2072 CFX_WideString swMsg;
2073 swMsg.Format(JSGetStringFromID(pContext, IDS_STRING_JSPARSEDATE), (FX_LPCWSTR)sFormat);
2074 Alert((CJS_Context *)cc, swMsg);
2075 return FALSE;
2076 }
2077
2078 vRet = dDate;
2079
2080 return TRUE;
2081}
2082
2083FX_BOOL CJS_PublicMethods::AFSimple(OBJ_METHOD_PARAMS)
2084{
2085 if (params.size() != 3)
2086 {
2087 CJS_Context* pContext = (CJS_Context *)cc;
2088 ASSERT(pContext != NULL);
2089
2090 sError = JSGetStringFromID(pContext, IDS_STRING_JSPARAMERROR);
2091 return FALSE;
2092 }
2093
2094 vRet = (double)AF_Simple(params[0].operator CFX_WideString(), (double)params[1], (double)params[2]);
2095 return TRUE;
2096}
2097
2098FX_BOOL CJS_PublicMethods::AFMakeNumber(OBJ_METHOD_PARAMS)
2099{
2100 if (params.size() != 1)
2101 {
2102 CJS_Context* pContext = (CJS_Context *)cc;
2103 ASSERT(pContext != NULL);
2104
2105 sError = JSGetStringFromID(pContext, IDS_STRING_JSPARAMERROR);
2106 return FALSE;
2107 }
2108 vRet = ParseStringToNumber(params[0].operator CFX_WideString());
2109 return TRUE;
2110}
2111
2112FX_BOOL CJS_PublicMethods::AFSimple_Calculate(OBJ_METHOD_PARAMS)
2113{
2114 v8::Isolate* isolate = ::GetIsolate(cc);
2115
2116 CJS_Context* pContext = (CJS_Context *)cc;
2117 ASSERT(pContext != NULL);
2118
2119 if (params.size() != 2)
2120 {
2121 sError = JSGetStringFromID(pContext, IDS_STRING_JSPARAMERROR);
2122 return FALSE;
2123 }
2124
2125 CJS_Value params1 = params[1];
2126
2127 if (!params1.IsArrayObject() && params1.GetType() != VT_string)
2128 {
2129 sError = JSGetStringFromID(pContext, IDS_STRING_JSPARAMERROR);
2130 return FALSE;
2131 }
2132
2133 CPDFSDK_Document* pReaderDoc = pContext->GetReaderDocument();
2134 ASSERT(pReaderDoc != NULL);
2135
2136 CPDFSDK_InterForm* pReaderInterForm = pReaderDoc->GetInterForm();
2137 ASSERT(pReaderInterForm != NULL);
2138
2139 CPDF_InterForm* pInterForm = pReaderInterForm->GetInterForm();
2140 ASSERT(pInterForm != NULL);
2141
2142 double dValue;
2143 CFX_WideString sFunction = params[0].operator CFX_WideString();
2144 if (wcscmp(sFunction, L"PRD") == 0)
2145 dValue = 1.0;
2146 else
2147 dValue = 0.0;
2148
2149 CJS_Array FieldNameArray = AF_MakeArrayFromList(isolate,params1);
2150
2151 int nFieldsCount = 0;
2152
2153 for (int i=0,isz=FieldNameArray.GetLength(); i<isz; i++)
2154 {
2155 CJS_Value jsValue(isolate);
2156 FieldNameArray.GetElement(i,jsValue);
2157 CFX_WideString wsFieldName = jsValue.operator CFX_WideString();
2158
2159 for (int j=0,jsz=pInterForm->CountFields(wsFieldName); j<jsz; j++)
2160 {
2161 if (CPDF_FormField* pFormField = pInterForm->GetField(j, wsFieldName))
2162 {
2163 double dTemp = 0.0;
2164
2165 switch (pFormField->GetFieldType())
2166 {
2167 case FIELDTYPE_TEXTFIELD:
2168 case FIELDTYPE_COMBOBOX:
2169 {
2170 dTemp = ParseStringToNumber(pFormField->GetValue());
2171 break;
2172 }
2173 case FIELDTYPE_PUSHBUTTON:
2174 {
2175 dTemp = 0.0;
2176 break;
2177 }
2178 case FIELDTYPE_CHECKBOX:
2179 case FIELDTYPE_RADIOBUTTON:
2180 {
2181 dTemp = 0.0;
2182 for (int c=0,csz=pFormField->CountControls(); c<csz; c++)
2183 {
2184 if (CPDF_FormControl* pFormCtrl = pFormField->GetControl(c))
2185 {
2186 if (pFormCtrl->IsChecked())
2187 {
2188 dTemp += ParseStringToNumber(pFormCtrl->GetExportValue());
2189 break;
2190 }
2191 else
2192 continue;
2193 }
2194 }
2195 break;
2196 }
2197 case FIELDTYPE_LISTBOX:
2198 {
2199 dTemp = 0.0;
2200 if (pFormField->CountSelectedItems() > 1)
2201 break;
2202 else
2203 {
2204 dTemp = ParseStringToNumber(pFormField->GetValue());
2205 break;
2206 }
2207 }
2208 default:
2209 break;
2210 }
2211
2212 if (i == 0 && j == 0 && (wcscmp(sFunction,L"MIN") == 0 || wcscmp(sFunction, L"MAX") == 0))
2213 dValue = dTemp;
2214
2215 dValue = AF_Simple(sFunction, dValue, dTemp);
2216
2217 nFieldsCount++;
2218 }
2219 }
2220 }
2221
2222 if (wcscmp(sFunction, L"AVG") == 0 && nFieldsCount > 0)
2223 dValue /= nFieldsCount;
2224
2225 dValue = (double)floor(dValue * FXSYS_pow((double)10,(double)6) + 0.49) / FXSYS_pow((double)10,(double)6);
2226 CJS_Value jsValue(isolate,dValue);
2227 if((CJS_EventHandler*)pContext->GetEventHandler()->m_pValue)
2228 ((CJS_EventHandler*)pContext->GetEventHandler())->Value() = jsValue;
2229
2230 return TRUE;
2231}
2232
2233/* This function validates the current event to ensure that its value is
2234** within the specified range. */
2235
2236FX_BOOL CJS_PublicMethods::AFRange_Validate(OBJ_METHOD_PARAMS)
2237{
2238 CJS_Context* pContext = (CJS_Context *)cc;
2239 ASSERT(pContext != NULL);
2240 CJS_EventHandler* pEvent = pContext->GetEventHandler();
2241 ASSERT(pEvent != NULL);
2242
2243 if (params.size() != 4)
2244 {
2245 sError = JSGetStringFromID(pContext, IDS_STRING_JSPARAMERROR);
2246 return FALSE;
2247 }
2248
2249 if(!pEvent->m_pValue)
2250 return FALSE;
2251 if (pEvent->Value().IsEmpty() )
2252 return TRUE;
2253 double dEentValue = atof(CFX_ByteString::FromUnicode(pEvent->Value()));
2254 FX_BOOL bGreaterThan, bLessThan;
2255 double dGreaterThan, dLessThan;
2256 bGreaterThan = (FX_BOOL)params[0];
2257 CFX_WideString swMsg;
2258 dGreaterThan = (double)params[1];
2259 bLessThan = (FX_BOOL)params[2];
2260 dLessThan = (double)params[3];
2261
2262 if (bGreaterThan && bLessThan)
2263 {
2264 if (dEentValue < dGreaterThan || dEentValue > dLessThan)
2265 swMsg.Format(JSGetStringFromID(pContext, IDS_STRING_JSRANGE1),(FX_LPCWSTR)params[1].operator CFX_WideString(), (FX_LPCWSTR)params[3].operator CFX_WideString());
2266 }
2267 else if (bGreaterThan)
2268 {
2269 if (dEentValue < dGreaterThan)
2270 swMsg.Format(JSGetStringFromID(pContext, IDS_STRING_JSRANGE2), (FX_LPCWSTR)params[1].operator CFX_WideString());
2271 }
2272 else if (bLessThan)
2273 {
2274 if (dEentValue > dLessThan)
2275 swMsg.Format(JSGetStringFromID(pContext, IDS_STRING_JSRANGE3), (FX_LPCWSTR)params[3].operator CFX_WideString());
2276 }
2277
2278 if (!swMsg.IsEmpty())
2279 {
2280 Alert(pContext, swMsg);
2281 pEvent->Rc() = FALSE;
2282 }
2283 return TRUE;
2284}
2285
2286FX_BOOL CJS_PublicMethods::AFExtractNums(OBJ_METHOD_PARAMS)
2287{
2288 v8::Isolate* isolate = ::GetIsolate(cc);
2289 CJS_Context* pContext = (CJS_Context*)cc;
2290 ASSERT(pContext != NULL);
2291
2292 if (params.size() != 1)
2293 {
2294 sError = JSGetStringFromID(pContext, IDS_STRING_JSPARAMERROR);
2295 return FALSE;
2296 }
2297
2298 CJS_Array nums(isolate);
2299
2300 CFX_WideString str = params[0].operator CFX_WideString();
2301 CFX_WideString sPart;
2302
2303 if (str.GetAt(0) == L'.' || str.GetAt(0) == L',')
2304 str = L"0" + str;
2305
2306 int nIndex = 0;
2307 for (int i=0, sz=str.GetLength(); i<sz; i++)
2308 {
2309 FX_WCHAR wc = str.GetAt(i);
2310 if (IsDigit((wchar_t)wc))
2311 {
2312 sPart += wc;
2313 }
2314 else
2315 {
2316 if (sPart.GetLength() > 0)
2317 {
2318 nums.SetElement(nIndex,CJS_Value(isolate,(FX_LPCWSTR)sPart));
2319 sPart = L"";
2320 nIndex ++;
2321 }
2322 }
2323 }
2324
2325 if (sPart.GetLength() > 0)
2326 {
2327 nums.SetElement(nIndex,CJS_Value(isolate,(FX_LPCWSTR)sPart));
2328 }
2329
2330 if (nums.GetLength() > 0)
2331 vRet = nums;
2332 else
2333 vRet.SetNull();
2334
2335 return TRUE;
2336}