blob: 2495897408db4d708f036400516f703604f14b0b [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.
Lei Zhanga6d9f0e2015-06-13 00:48:38 -07004
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -07005// Original code copyright 2014 Foxit Software Inc. http://www.foxitsoftware.com
6
Lei Zhang375a8642016-01-11 11:59:17 -08007#include <algorithm>
8
Dan Sinclair10cfea12015-11-16 13:09:00 -05009#include "core/include/fxcrt/fx_ext.h"
Lei Zhangbde53d22015-11-12 22:21:30 -080010#include "fpdfsdk/include/fsdk_baseannot.h"
11#include "fpdfsdk/include/fsdk_define.h"
12#include "fpdfsdk/include/fsdk_mgr.h"
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -070013
Tom Sepez40e9ff32015-11-30 12:39:54 -080014#ifdef PDF_ENABLE_XFA
15#include "fpdfsdk/include/fpdfxfa/fpdfxfa_doc.h"
16#endif // PDF_ENABLE_XFA
17
Nico Weber9d8ec5a2015-08-04 13:00:21 -070018int _gAfxGetTimeZoneInSeconds(FX_CHAR tzhour, uint8_t tzminute) {
19 return (int)tzhour * 3600 + (int)tzminute * (tzhour >= 0 ? 60 : -60);
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -070020}
21
Nico Weber9d8ec5a2015-08-04 13:00:21 -070022FX_BOOL _gAfxIsLeapYear(int16_t year) {
23 return ((year % 400 == 0) || ((year % 4 == 0) && (year % 100 != 0)));
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -070024}
25
Nico Weber9d8ec5a2015-08-04 13:00:21 -070026FX_WORD _gAfxGetYearDays(int16_t year) {
27 return (_gAfxIsLeapYear(year) == TRUE ? 366 : 365);
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -070028}
29
Nico Weber9d8ec5a2015-08-04 13:00:21 -070030uint8_t _gAfxGetMonthDays(int16_t year, uint8_t month) {
31 uint8_t mDays;
32 switch (month) {
Tom Sepez2f2ffec2015-07-23 14:42:09 -070033 case 1:
34 case 3:
35 case 5:
36 case 7:
37 case 8:
38 case 10:
39 case 12:
Nico Weber9d8ec5a2015-08-04 13:00:21 -070040 mDays = 31;
41 break;
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -070042
Tom Sepez2f2ffec2015-07-23 14:42:09 -070043 case 4:
44 case 6:
45 case 9:
46 case 11:
Nico Weber9d8ec5a2015-08-04 13:00:21 -070047 mDays = 30;
48 break;
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -070049
Tom Sepez2f2ffec2015-07-23 14:42:09 -070050 case 2:
Nico Weber9d8ec5a2015-08-04 13:00:21 -070051 if (_gAfxIsLeapYear(year) == TRUE)
52 mDays = 29;
53 else
54 mDays = 28;
55 break;
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -070056
Tom Sepez2f2ffec2015-07-23 14:42:09 -070057 default:
Nico Weber9d8ec5a2015-08-04 13:00:21 -070058 mDays = 0;
59 break;
60 }
61
62 return mDays;
63}
64
65CPDFSDK_DateTime::CPDFSDK_DateTime() {
66 ResetDateTime();
67}
68
69CPDFSDK_DateTime::CPDFSDK_DateTime(const CFX_ByteString& dtStr) {
70 ResetDateTime();
71
72 FromPDFDateTimeString(dtStr);
73}
74
75CPDFSDK_DateTime::CPDFSDK_DateTime(const CPDFSDK_DateTime& datetime) {
76 operator=(datetime);
77}
78
79CPDFSDK_DateTime::CPDFSDK_DateTime(const FX_SYSTEMTIME& st) {
80 operator=(st);
81}
82
83void CPDFSDK_DateTime::ResetDateTime() {
84 tzset();
85
86 time_t curTime;
87 time(&curTime);
88 struct tm* newtime;
89 // newtime = gmtime(&curTime);
90 newtime = localtime(&curTime);
91
92 dt.year = newtime->tm_year + 1900;
93 dt.month = newtime->tm_mon + 1;
94 dt.day = newtime->tm_mday;
95 dt.hour = newtime->tm_hour;
96 dt.minute = newtime->tm_min;
97 dt.second = newtime->tm_sec;
98 // dt.tzHour = _timezone / 3600 * -1;
99 // dt.tzMinute = (abs(_timezone) % 3600) / 60;
100}
101
102CPDFSDK_DateTime& CPDFSDK_DateTime::operator=(
103 const CPDFSDK_DateTime& datetime) {
104 FXSYS_memcpy(&dt, &datetime.dt, sizeof(FX_DATETIME));
105 return *this;
106}
107
108CPDFSDK_DateTime& CPDFSDK_DateTime::operator=(const FX_SYSTEMTIME& st) {
109 tzset();
110
111 dt.year = (int16_t)st.wYear;
112 dt.month = (uint8_t)st.wMonth;
113 dt.day = (uint8_t)st.wDay;
114 dt.hour = (uint8_t)st.wHour;
115 dt.minute = (uint8_t)st.wMinute;
116 dt.second = (uint8_t)st.wSecond;
117 // dt.tzHour = _timezone / 3600 * -1;
118 // dt.tzMinute = (abs(_timezone) % 3600) / 60;
119 return *this;
120}
121
122FX_BOOL CPDFSDK_DateTime::operator==(CPDFSDK_DateTime& datetime) {
123 return (FXSYS_memcmp(&dt, &datetime.dt, sizeof(FX_DATETIME)) == 0);
124}
125
126FX_BOOL CPDFSDK_DateTime::operator!=(CPDFSDK_DateTime& datetime) {
127 return (FXSYS_memcmp(&dt, &datetime.dt, sizeof(FX_DATETIME)) != 0);
128}
129
130FX_BOOL CPDFSDK_DateTime::operator>(CPDFSDK_DateTime& datetime) {
131 CPDFSDK_DateTime dt1 = ToGMT();
132 CPDFSDK_DateTime dt2 = datetime.ToGMT();
133 int d1 =
134 (((int)dt1.dt.year) << 16) | (((int)dt1.dt.month) << 8) | (int)dt1.dt.day;
135 int d2 = (((int)dt1.dt.hour) << 16) | (((int)dt1.dt.minute) << 8) |
136 (int)dt1.dt.second;
137 int d3 =
138 (((int)dt2.dt.year) << 16) | (((int)dt2.dt.month) << 8) | (int)dt2.dt.day;
139 int d4 = (((int)dt2.dt.hour) << 16) | (((int)dt2.dt.minute) << 8) |
140 (int)dt2.dt.second;
141
142 if (d1 > d3)
143 return TRUE;
144 if (d2 > d4)
145 return TRUE;
146 return FALSE;
147}
148
149FX_BOOL CPDFSDK_DateTime::operator>=(CPDFSDK_DateTime& datetime) {
150 CPDFSDK_DateTime dt1 = ToGMT();
151 CPDFSDK_DateTime dt2 = datetime.ToGMT();
152 int d1 =
153 (((int)dt1.dt.year) << 16) | (((int)dt1.dt.month) << 8) | (int)dt1.dt.day;
154 int d2 = (((int)dt1.dt.hour) << 16) | (((int)dt1.dt.minute) << 8) |
155 (int)dt1.dt.second;
156 int d3 =
157 (((int)dt2.dt.year) << 16) | (((int)dt2.dt.month) << 8) | (int)dt2.dt.day;
158 int d4 = (((int)dt2.dt.hour) << 16) | (((int)dt2.dt.minute) << 8) |
159 (int)dt2.dt.second;
160
161 if (d1 >= d3)
162 return TRUE;
163 if (d2 >= d4)
164 return TRUE;
165 return FALSE;
166}
167
168FX_BOOL CPDFSDK_DateTime::operator<(CPDFSDK_DateTime& datetime) {
169 CPDFSDK_DateTime dt1 = ToGMT();
170 CPDFSDK_DateTime dt2 = datetime.ToGMT();
171 int d1 =
172 (((int)dt1.dt.year) << 16) | (((int)dt1.dt.month) << 8) | (int)dt1.dt.day;
173 int d2 = (((int)dt1.dt.hour) << 16) | (((int)dt1.dt.minute) << 8) |
174 (int)dt1.dt.second;
175 int d3 =
176 (((int)dt2.dt.year) << 16) | (((int)dt2.dt.month) << 8) | (int)dt2.dt.day;
177 int d4 = (((int)dt2.dt.hour) << 16) | (((int)dt2.dt.minute) << 8) |
178 (int)dt2.dt.second;
179
180 if (d1 < d3)
181 return TRUE;
182 if (d2 < d4)
183 return TRUE;
184 return FALSE;
185}
186
187FX_BOOL CPDFSDK_DateTime::operator<=(CPDFSDK_DateTime& datetime) {
188 CPDFSDK_DateTime dt1 = ToGMT();
189 CPDFSDK_DateTime dt2 = datetime.ToGMT();
190 int d1 =
191 (((int)dt1.dt.year) << 16) | (((int)dt1.dt.month) << 8) | (int)dt1.dt.day;
192 int d2 = (((int)dt1.dt.hour) << 16) | (((int)dt1.dt.minute) << 8) |
193 (int)dt1.dt.second;
194 int d3 =
195 (((int)dt2.dt.year) << 16) | (((int)dt2.dt.month) << 8) | (int)dt2.dt.day;
196 int d4 = (((int)dt2.dt.hour) << 16) | (((int)dt2.dt.minute) << 8) |
197 (int)dt2.dt.second;
198
199 if (d1 <= d3)
200 return TRUE;
201 if (d2 <= d4)
202 return TRUE;
203 return FALSE;
204}
205
206CPDFSDK_DateTime::operator time_t() {
207 struct tm newtime;
208
209 newtime.tm_year = dt.year - 1900;
210 newtime.tm_mon = dt.month - 1;
211 newtime.tm_mday = dt.day;
212 newtime.tm_hour = dt.hour;
213 newtime.tm_min = dt.minute;
214 newtime.tm_sec = dt.second;
215
216 return mktime(&newtime);
217}
218
219CPDFSDK_DateTime& CPDFSDK_DateTime::FromPDFDateTimeString(
220 const CFX_ByteString& dtStr) {
221 int strLength = dtStr.GetLength();
222 if (strLength > 0) {
223 int i = 0;
224 int j, k;
225 FX_CHAR ch;
Dan Sinclair10cfea12015-11-16 13:09:00 -0500226 while (i < strLength && !std::isdigit(dtStr[i]))
227 ++i;
228
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700229 if (i >= strLength)
230 return *this;
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700231
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700232 j = 0;
233 k = 0;
234 while (i < strLength && j < 4) {
235 ch = dtStr[i];
Dan Sinclair10cfea12015-11-16 13:09:00 -0500236 k = k * 10 + FXSYS_toDecimalDigit(ch);
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700237 j++;
Dan Sinclair10cfea12015-11-16 13:09:00 -0500238 if (!std::isdigit(ch))
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700239 break;
240 i++;
Tom Sepez2f2ffec2015-07-23 14:42:09 -0700241 }
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700242 dt.year = (int16_t)k;
243 if (i >= strLength || j < 4)
244 return *this;
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700245
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700246 j = 0;
247 k = 0;
248 while (i < strLength && j < 2) {
249 ch = dtStr[i];
Dan Sinclair10cfea12015-11-16 13:09:00 -0500250 k = k * 10 + FXSYS_toDecimalDigit(ch);
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700251 j++;
Dan Sinclair10cfea12015-11-16 13:09:00 -0500252 if (!std::isdigit(ch))
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700253 break;
254 i++;
255 }
256 dt.month = (uint8_t)k;
257 if (i >= strLength || j < 2)
258 return *this;
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700259
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700260 j = 0;
261 k = 0;
262 while (i < strLength && j < 2) {
263 ch = dtStr[i];
Dan Sinclair10cfea12015-11-16 13:09:00 -0500264 k = k * 10 + FXSYS_toDecimalDigit(ch);
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700265 j++;
Dan Sinclair10cfea12015-11-16 13:09:00 -0500266 if (!std::isdigit(ch))
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700267 break;
268 i++;
269 }
270 dt.day = (uint8_t)k;
271 if (i >= strLength || j < 2)
272 return *this;
273
274 j = 0;
275 k = 0;
276 while (i < strLength && j < 2) {
277 ch = dtStr[i];
Dan Sinclair10cfea12015-11-16 13:09:00 -0500278 k = k * 10 + FXSYS_toDecimalDigit(ch);
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700279 j++;
Dan Sinclair10cfea12015-11-16 13:09:00 -0500280 if (!std::isdigit(ch))
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700281 break;
282 i++;
283 }
284 dt.hour = (uint8_t)k;
285 if (i >= strLength || j < 2)
286 return *this;
287
288 j = 0;
289 k = 0;
290 while (i < strLength && j < 2) {
291 ch = dtStr[i];
Dan Sinclair10cfea12015-11-16 13:09:00 -0500292 k = k * 10 + FXSYS_toDecimalDigit(ch);
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700293 j++;
Dan Sinclair10cfea12015-11-16 13:09:00 -0500294 if (!std::isdigit(ch))
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700295 break;
296 i++;
297 }
298 dt.minute = (uint8_t)k;
299 if (i >= strLength || j < 2)
300 return *this;
301
302 j = 0;
303 k = 0;
304 while (i < strLength && j < 2) {
305 ch = dtStr[i];
Dan Sinclair10cfea12015-11-16 13:09:00 -0500306 k = k * 10 + FXSYS_toDecimalDigit(ch);
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700307 j++;
Dan Sinclair10cfea12015-11-16 13:09:00 -0500308 if (!std::isdigit(ch))
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700309 break;
310 i++;
311 }
312 dt.second = (uint8_t)k;
313 if (i >= strLength || j < 2)
314 return *this;
315
316 ch = dtStr[i++];
317 if (ch != '-' && ch != '+')
318 return *this;
319 if (ch == '-')
320 dt.tzHour = -1;
Tom Sepez2f2ffec2015-07-23 14:42:09 -0700321 else
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700322 dt.tzHour = 1;
323 j = 0;
324 k = 0;
325 while (i < strLength && j < 2) {
326 ch = dtStr[i];
Dan Sinclair10cfea12015-11-16 13:09:00 -0500327 k = k * 10 + FXSYS_toDecimalDigit(ch);
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700328 j++;
Dan Sinclair10cfea12015-11-16 13:09:00 -0500329 if (!std::isdigit(ch))
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700330 break;
331 i++;
Tom Sepez2f2ffec2015-07-23 14:42:09 -0700332 }
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700333 dt.tzHour *= (FX_CHAR)k;
334 if (i >= strLength || j < 2)
335 return *this;
336
337 ch = dtStr[i++];
338 if (ch != '\'')
339 return *this;
340 j = 0;
341 k = 0;
342 while (i < strLength && j < 2) {
343 ch = dtStr[i];
Dan Sinclair10cfea12015-11-16 13:09:00 -0500344 k = k * 10 + FXSYS_toDecimalDigit(ch);
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700345 j++;
Dan Sinclair10cfea12015-11-16 13:09:00 -0500346 if (!std::isdigit(ch))
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700347 break;
348 i++;
349 }
350 dt.tzMinute = (uint8_t)k;
351 if (i >= strLength || j < 2)
352 return *this;
353 }
354
355 return *this;
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700356}
357
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700358CFX_ByteString CPDFSDK_DateTime::ToCommonDateTimeString() {
359 CFX_ByteString str1;
360 str1.Format("%04d-%02d-%02d %02d:%02d:%02d ", dt.year, dt.month, dt.day,
361 dt.hour, dt.minute, dt.second);
362 if (dt.tzHour < 0)
363 str1 += "-";
364 else
365 str1 += "+";
366 CFX_ByteString str2;
367 str2.Format("%02d:%02d", abs(dt.tzHour), dt.tzMinute);
368 return str1 + str2;
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700369}
370
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700371CFX_ByteString CPDFSDK_DateTime::ToPDFDateTimeString() {
372 CFX_ByteString dtStr;
373 char tempStr[32];
374 memset(tempStr, 0, sizeof(tempStr));
375 FXSYS_snprintf(tempStr, sizeof(tempStr) - 1, "D:%04d%02d%02d%02d%02d%02d",
376 dt.year, dt.month, dt.day, dt.hour, dt.minute, dt.second);
377 dtStr = CFX_ByteString(tempStr);
378 if (dt.tzHour < 0)
379 dtStr += CFX_ByteString("-");
380 else
381 dtStr += CFX_ByteString("+");
382 memset(tempStr, 0, sizeof(tempStr));
383 FXSYS_snprintf(tempStr, sizeof(tempStr) - 1, "%02d'%02d'", abs(dt.tzHour),
384 dt.tzMinute);
385 dtStr += CFX_ByteString(tempStr);
386 return dtStr;
387}
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700388
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700389void CPDFSDK_DateTime::ToSystemTime(FX_SYSTEMTIME& st) {
390 CPDFSDK_DateTime dt = *this;
391 time_t t = (time_t)dt;
392 struct tm* pTime = localtime(&t);
393 if (pTime) {
394 st.wYear = (FX_WORD)pTime->tm_year + 1900;
395 st.wMonth = (FX_WORD)pTime->tm_mon + 1;
396 st.wDay = (FX_WORD)pTime->tm_mday;
397 st.wDayOfWeek = (FX_WORD)pTime->tm_wday;
398 st.wHour = (FX_WORD)pTime->tm_hour;
399 st.wMinute = (FX_WORD)pTime->tm_min;
400 st.wSecond = (FX_WORD)pTime->tm_sec;
401 st.wMilliseconds = 0;
402 }
403}
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700404
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700405CPDFSDK_DateTime CPDFSDK_DateTime::ToGMT() {
406 CPDFSDK_DateTime dt = *this;
407 dt.AddSeconds(-_gAfxGetTimeZoneInSeconds(dt.dt.tzHour, dt.dt.tzMinute));
408 dt.dt.tzHour = 0;
409 dt.dt.tzMinute = 0;
410 return dt;
411}
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700412
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700413CPDFSDK_DateTime& CPDFSDK_DateTime::AddDays(short days) {
414 if (days == 0)
Tom Sepez2f2ffec2015-07-23 14:42:09 -0700415 return *this;
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700416
417 int16_t y = dt.year, yy;
418 uint8_t m = dt.month;
419 uint8_t d = dt.day;
420 int mdays, ydays, ldays;
421
422 ldays = days;
423 if (ldays > 0) {
424 yy = y;
425 if (((FX_WORD)m * 100 + d) > 300)
426 yy++;
427 ydays = _gAfxGetYearDays(yy);
428 while (ldays >= ydays) {
429 y++;
430 ldays -= ydays;
431 yy++;
432 mdays = _gAfxGetMonthDays(y, m);
433 if (d > mdays) {
434 m++;
435 d -= mdays;
436 }
437 ydays = _gAfxGetYearDays(yy);
438 }
439 mdays = _gAfxGetMonthDays(y, m) - d + 1;
440 while (ldays >= mdays) {
441 ldays -= mdays;
442 m++;
443 d = 1;
444 mdays = _gAfxGetMonthDays(y, m);
445 }
446 d += ldays;
447 } else {
448 ldays *= -1;
449 yy = y;
450 if (((FX_WORD)m * 100 + d) < 300)
451 yy--;
452 ydays = _gAfxGetYearDays(yy);
453 while (ldays >= ydays) {
454 y--;
455 ldays -= ydays;
456 yy--;
457 mdays = _gAfxGetMonthDays(y, m);
458 if (d > mdays) {
459 m++;
460 d -= mdays;
461 }
462 ydays = _gAfxGetYearDays(yy);
463 }
464 while (ldays >= d) {
465 ldays -= d;
466 m--;
467 mdays = _gAfxGetMonthDays(y, m);
468 d = mdays;
469 }
470 d -= ldays;
471 }
472
473 dt.year = y;
474 dt.month = m;
475 dt.day = d;
476
477 return *this;
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700478}
479
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700480CPDFSDK_DateTime& CPDFSDK_DateTime::AddSeconds(int seconds) {
481 if (seconds == 0)
Tom Sepez2f2ffec2015-07-23 14:42:09 -0700482 return *this;
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700483
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700484 int n;
485 int days;
486
487 n = dt.hour * 3600 + dt.minute * 60 + dt.second + seconds;
488 if (n < 0) {
489 days = (n - 86399) / 86400;
490 n -= days * 86400;
491 } else {
492 days = n / 86400;
493 n %= 86400;
494 }
495 dt.hour = (uint8_t)(n / 3600);
496 dt.hour %= 24;
497 n %= 3600;
498 dt.minute = (uint8_t)(n / 60);
499 dt.second = (uint8_t)(n % 60);
500 if (days != 0)
501 AddDays(days);
502
503 return *this;
504}
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700505
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700506CPDFSDK_Annot::CPDFSDK_Annot(CPDFSDK_PageView* pPageView)
Dan Sinclairbfe042a2015-11-04 14:04:13 -0500507 : m_pPageView(pPageView), m_bSelected(FALSE), m_nTabOrder(-1) {
508}
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700509
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700510CPDFSDK_BAAnnot::CPDFSDK_BAAnnot(CPDF_Annot* pAnnot,
511 CPDFSDK_PageView* pPageView)
Dan Sinclairbfe042a2015-11-04 14:04:13 -0500512 : CPDFSDK_Annot(pPageView), m_pAnnot(pAnnot) {
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700513}
514
Tom Sepez3343d142015-11-02 09:54:54 -0800515CPDF_Annot* CPDFSDK_BAAnnot::GetPDFAnnot() const {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700516 return m_pAnnot;
Bo Xufdc00a72014-10-28 23:03:33 -0700517}
518
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700519FX_BOOL CPDFSDK_Annot::IsSelected() {
520 return m_bSelected;
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700521}
522
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700523void CPDFSDK_Annot::SetSelected(FX_BOOL bSelected) {
524 m_bSelected = bSelected;
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700525}
526
Lei Zhanga6d9f0e2015-06-13 00:48:38 -0700527// Tab Order
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700528int CPDFSDK_Annot::GetTabOrder() {
529 return m_nTabOrder;
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700530}
531
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700532void CPDFSDK_Annot::SetTabOrder(int iTabOrder) {
533 m_nTabOrder = iTabOrder;
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700534}
535
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700536CPDF_Dictionary* CPDFSDK_BAAnnot::GetAnnotDict() const {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700537 return m_pAnnot->GetAnnotDict();
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700538}
539
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700540void CPDFSDK_BAAnnot::SetRect(const CPDF_Rect& rect) {
541 ASSERT(rect.right - rect.left >= GetMinWidth());
542 ASSERT(rect.top - rect.bottom >= GetMinHeight());
Lei Zhanga6d9f0e2015-06-13 00:48:38 -0700543
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700544 m_pAnnot->GetAnnotDict()->SetAtRect("Rect", rect);
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700545}
546
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700547CPDF_Rect CPDFSDK_BAAnnot::GetRect() const {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700548 CPDF_Rect rect;
549 m_pAnnot->GetRect(rect);
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700550 return rect;
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700551}
552
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700553CFX_ByteString CPDFSDK_BAAnnot::GetType() const {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700554 return m_pAnnot->GetSubType();
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700555}
556
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700557CFX_ByteString CPDFSDK_BAAnnot::GetSubType() const {
558 return "";
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700559}
560
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700561void CPDFSDK_BAAnnot::DrawAppearance(CFX_RenderDevice* pDevice,
Tom Sepez60d909e2015-12-10 15:34:55 -0800562 const CFX_Matrix* pUser2Device,
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700563 CPDF_Annot::AppearanceMode mode,
564 const CPDF_RenderOptions* pOptions) {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700565 m_pAnnot->DrawAppearance(m_pPageView->GetPDFPage(), pDevice, pUser2Device,
566 mode, pOptions);
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700567}
568
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700569FX_BOOL CPDFSDK_BAAnnot::IsAppearanceValid() {
Wei Li9b761132016-01-29 15:44:20 -0800570 return m_pAnnot->GetAnnotDict()->GetDictBy("AP") != NULL;
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700571}
572
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700573FX_BOOL CPDFSDK_BAAnnot::IsAppearanceValid(CPDF_Annot::AppearanceMode mode) {
Wei Li9b761132016-01-29 15:44:20 -0800574 CPDF_Dictionary* pAP = m_pAnnot->GetAnnotDict()->GetDictBy("AP");
Lei Zhang412e9082015-12-14 18:34:00 -0800575 if (!pAP)
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700576 return FALSE;
Lei Zhanga6d9f0e2015-06-13 00:48:38 -0700577
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700578 // Choose the right sub-ap
579 const FX_CHAR* ap_entry = "N";
580 if (mode == CPDF_Annot::Down)
581 ap_entry = "D";
582 else if (mode == CPDF_Annot::Rollover)
583 ap_entry = "R";
584 if (!pAP->KeyExist(ap_entry))
585 ap_entry = "N";
Lei Zhanga6d9f0e2015-06-13 00:48:38 -0700586
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700587 // Get the AP stream or subdirectory
588 CPDF_Object* psub = pAP->GetElementValue(ap_entry);
Lei Zhang412e9082015-12-14 18:34:00 -0800589 return !!psub;
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700590}
591
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700592void CPDFSDK_BAAnnot::DrawBorder(CFX_RenderDevice* pDevice,
Tom Sepez60d909e2015-12-10 15:34:55 -0800593 const CFX_Matrix* pUser2Device,
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700594 const CPDF_RenderOptions* pOptions) {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700595 m_pAnnot->DrawBorder(pDevice, pUser2Device, pOptions);
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700596}
597
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700598void CPDFSDK_BAAnnot::ClearCachedAP() {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700599 m_pAnnot->ClearCachedAP();
Lei Zhanga6d9f0e2015-06-13 00:48:38 -0700600}
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700601
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700602void CPDFSDK_BAAnnot::SetContents(const CFX_WideString& sContents) {
603 if (sContents.IsEmpty())
604 m_pAnnot->GetAnnotDict()->RemoveAt("Contents");
605 else
606 m_pAnnot->GetAnnotDict()->SetAtString("Contents",
607 PDF_EncodeText(sContents));
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700608}
609
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700610CFX_WideString CPDFSDK_BAAnnot::GetContents() const {
Wei Li9b761132016-01-29 15:44:20 -0800611 return m_pAnnot->GetAnnotDict()->GetUnicodeTextBy("Contents");
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700612}
613
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700614void CPDFSDK_BAAnnot::SetAnnotName(const CFX_WideString& sName) {
615 if (sName.IsEmpty())
616 m_pAnnot->GetAnnotDict()->RemoveAt("NM");
617 else
618 m_pAnnot->GetAnnotDict()->SetAtString("NM", PDF_EncodeText(sName));
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700619}
620
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700621CFX_WideString CPDFSDK_BAAnnot::GetAnnotName() const {
Wei Li9b761132016-01-29 15:44:20 -0800622 return m_pAnnot->GetAnnotDict()->GetUnicodeTextBy("NM");
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700623}
624
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700625void CPDFSDK_BAAnnot::SetModifiedDate(const FX_SYSTEMTIME& st) {
626 CPDFSDK_DateTime dt(st);
627 CFX_ByteString str = dt.ToPDFDateTimeString();
Lei Zhanga6d9f0e2015-06-13 00:48:38 -0700628
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700629 if (str.IsEmpty())
630 m_pAnnot->GetAnnotDict()->RemoveAt("M");
631 else
632 m_pAnnot->GetAnnotDict()->SetAtString("M", str);
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700633}
634
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700635FX_SYSTEMTIME CPDFSDK_BAAnnot::GetModifiedDate() const {
636 FX_SYSTEMTIME systime;
Wei Li9b761132016-01-29 15:44:20 -0800637 CFX_ByteString str = m_pAnnot->GetAnnotDict()->GetStringBy("M");
Lei Zhanga6d9f0e2015-06-13 00:48:38 -0700638
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700639 CPDFSDK_DateTime dt(str);
640 dt.ToSystemTime(systime);
Lei Zhanga6d9f0e2015-06-13 00:48:38 -0700641
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700642 return systime;
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700643}
644
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700645void CPDFSDK_BAAnnot::SetFlags(int nFlags) {
646 m_pAnnot->GetAnnotDict()->SetAtInteger("F", nFlags);
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700647}
648
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700649int CPDFSDK_BAAnnot::GetFlags() const {
Wei Li9b761132016-01-29 15:44:20 -0800650 return m_pAnnot->GetAnnotDict()->GetIntegerBy("F");
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700651}
652
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700653void CPDFSDK_BAAnnot::SetAppState(const CFX_ByteString& str) {
654 if (str.IsEmpty())
655 m_pAnnot->GetAnnotDict()->RemoveAt("AS");
656 else
657 m_pAnnot->GetAnnotDict()->SetAtString("AS", str);
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700658}
659
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700660CFX_ByteString CPDFSDK_BAAnnot::GetAppState() const {
Wei Li9b761132016-01-29 15:44:20 -0800661 return m_pAnnot->GetAnnotDict()->GetStringBy("AS");
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700662}
663
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700664void CPDFSDK_BAAnnot::SetStructParent(int key) {
665 m_pAnnot->GetAnnotDict()->SetAtInteger("StructParent", key);
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700666}
667
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700668int CPDFSDK_BAAnnot::GetStructParent() const {
Wei Li9b761132016-01-29 15:44:20 -0800669 return m_pAnnot->GetAnnotDict()->GetIntegerBy("StructParent");
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700670}
671
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700672// border
673void CPDFSDK_BAAnnot::SetBorderWidth(int nWidth) {
Wei Li9b761132016-01-29 15:44:20 -0800674 CPDF_Array* pBorder = m_pAnnot->GetAnnotDict()->GetArrayBy("Border");
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700675
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700676 if (pBorder) {
Tom Sepezae51c812015-08-05 12:34:06 -0700677 pBorder->SetAt(2, new CPDF_Number(nWidth));
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700678 } else {
Wei Li9b761132016-01-29 15:44:20 -0800679 CPDF_Dictionary* pBSDict = m_pAnnot->GetAnnotDict()->GetDictBy("BS");
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700680
681 if (!pBSDict) {
Tom Sepezae51c812015-08-05 12:34:06 -0700682 pBSDict = new CPDF_Dictionary;
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700683 m_pAnnot->GetAnnotDict()->SetAt("BS", pBSDict);
Tom Sepez2f2ffec2015-07-23 14:42:09 -0700684 }
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700685
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700686 pBSDict->SetAtInteger("W", nWidth);
687 }
688}
689
690int CPDFSDK_BAAnnot::GetBorderWidth() const {
Wei Li9b761132016-01-29 15:44:20 -0800691 if (CPDF_Array* pBorder = m_pAnnot->GetAnnotDict()->GetArrayBy("Border")) {
692 return pBorder->GetIntegerAt(2);
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700693 }
Wei Li9b761132016-01-29 15:44:20 -0800694 if (CPDF_Dictionary* pBSDict = m_pAnnot->GetAnnotDict()->GetDictBy("BS")) {
695 return pBSDict->GetIntegerBy("W", 1);
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700696 }
697 return 1;
698}
699
700void CPDFSDK_BAAnnot::SetBorderStyle(int nStyle) {
Wei Li9b761132016-01-29 15:44:20 -0800701 CPDF_Dictionary* pBSDict = m_pAnnot->GetAnnotDict()->GetDictBy("BS");
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700702 if (!pBSDict) {
703 pBSDict = new CPDF_Dictionary;
704 m_pAnnot->GetAnnotDict()->SetAt("BS", pBSDict);
705 }
706
707 switch (nStyle) {
Tom Sepez2f2ffec2015-07-23 14:42:09 -0700708 case BBS_SOLID:
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700709 pBSDict->SetAtName("S", "S");
710 break;
Tom Sepez2f2ffec2015-07-23 14:42:09 -0700711 case BBS_DASH:
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700712 pBSDict->SetAtName("S", "D");
713 break;
Tom Sepez2f2ffec2015-07-23 14:42:09 -0700714 case BBS_BEVELED:
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700715 pBSDict->SetAtName("S", "B");
716 break;
Tom Sepez2f2ffec2015-07-23 14:42:09 -0700717 case BBS_INSET:
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700718 pBSDict->SetAtName("S", "I");
719 break;
Tom Sepez2f2ffec2015-07-23 14:42:09 -0700720 case BBS_UNDERLINE:
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700721 pBSDict->SetAtName("S", "U");
722 break;
723 }
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700724}
725
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700726int CPDFSDK_BAAnnot::GetBorderStyle() const {
Wei Li9b761132016-01-29 15:44:20 -0800727 CPDF_Dictionary* pBSDict = m_pAnnot->GetAnnotDict()->GetDictBy("BS");
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700728 if (pBSDict) {
Wei Li9b761132016-01-29 15:44:20 -0800729 CFX_ByteString sBorderStyle = pBSDict->GetStringBy("S", "S");
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700730 if (sBorderStyle == "S")
731 return BBS_SOLID;
732 if (sBorderStyle == "D")
733 return BBS_DASH;
734 if (sBorderStyle == "B")
735 return BBS_BEVELED;
736 if (sBorderStyle == "I")
737 return BBS_INSET;
738 if (sBorderStyle == "U")
739 return BBS_UNDERLINE;
740 }
741
Wei Li9b761132016-01-29 15:44:20 -0800742 CPDF_Array* pBorder = m_pAnnot->GetAnnotDict()->GetArrayBy("Border");
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700743 if (pBorder) {
744 if (pBorder->GetCount() >= 4) {
Wei Li9b761132016-01-29 15:44:20 -0800745 CPDF_Array* pDP = pBorder->GetArrayAt(3);
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700746 if (pDP && pDP->GetCount() > 0)
747 return BBS_DASH;
748 }
749 }
750
751 return BBS_SOLID;
752}
753
754void CPDFSDK_BAAnnot::SetBorderDash(const CFX_IntArray& array) {
Wei Li9b761132016-01-29 15:44:20 -0800755 CPDF_Dictionary* pBSDict = m_pAnnot->GetAnnotDict()->GetDictBy("BS");
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700756 if (!pBSDict) {
757 pBSDict = new CPDF_Dictionary;
758 m_pAnnot->GetAnnotDict()->SetAt("BS", pBSDict);
759 }
760
Tom Sepezae51c812015-08-05 12:34:06 -0700761 CPDF_Array* pArray = new CPDF_Array;
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700762 for (int i = 0, sz = array.GetSize(); i < sz; i++) {
763 pArray->AddInteger(array[i]);
764 }
765
766 pBSDict->SetAt("D", pArray);
767}
768
769void CPDFSDK_BAAnnot::GetBorderDash(CFX_IntArray& array) const {
770 CPDF_Array* pDash = NULL;
771
Wei Li9b761132016-01-29 15:44:20 -0800772 CPDF_Array* pBorder = m_pAnnot->GetAnnotDict()->GetArrayBy("Border");
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700773 if (pBorder) {
Wei Li9b761132016-01-29 15:44:20 -0800774 pDash = pBorder->GetArrayAt(3);
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700775 } else {
Wei Li9b761132016-01-29 15:44:20 -0800776 CPDF_Dictionary* pBSDict = m_pAnnot->GetAnnotDict()->GetDictBy("BS");
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700777 if (pBSDict) {
Wei Li9b761132016-01-29 15:44:20 -0800778 pDash = pBSDict->GetArrayBy("D");
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700779 }
780 }
781
782 if (pDash) {
783 for (int i = 0, sz = pDash->GetCount(); i < sz; i++) {
Wei Li9b761132016-01-29 15:44:20 -0800784 array.Add(pDash->GetIntegerAt(i));
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700785 }
786 }
787}
788
789void CPDFSDK_BAAnnot::SetColor(FX_COLORREF color) {
790 CPDF_Array* pArray = new CPDF_Array;
791 pArray->AddNumber((FX_FLOAT)FXSYS_GetRValue(color) / 255.0f);
792 pArray->AddNumber((FX_FLOAT)FXSYS_GetGValue(color) / 255.0f);
793 pArray->AddNumber((FX_FLOAT)FXSYS_GetBValue(color) / 255.0f);
794 m_pAnnot->GetAnnotDict()->SetAt("C", pArray);
795}
796
797void CPDFSDK_BAAnnot::RemoveColor() {
798 m_pAnnot->GetAnnotDict()->RemoveAt("C");
799}
800
801FX_BOOL CPDFSDK_BAAnnot::GetColor(FX_COLORREF& color) const {
Wei Li9b761132016-01-29 15:44:20 -0800802 if (CPDF_Array* pEntry = m_pAnnot->GetAnnotDict()->GetArrayBy("C")) {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700803 int nCount = pEntry->GetCount();
804 if (nCount == 1) {
Wei Li9b761132016-01-29 15:44:20 -0800805 FX_FLOAT g = pEntry->GetNumberAt(0) * 255;
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700806
807 color = FXSYS_RGB((int)g, (int)g, (int)g);
808
809 return TRUE;
810 } else if (nCount == 3) {
Wei Li9b761132016-01-29 15:44:20 -0800811 FX_FLOAT r = pEntry->GetNumberAt(0) * 255;
812 FX_FLOAT g = pEntry->GetNumberAt(1) * 255;
813 FX_FLOAT b = pEntry->GetNumberAt(2) * 255;
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700814
815 color = FXSYS_RGB((int)r, (int)g, (int)b);
816
817 return TRUE;
818 } else if (nCount == 4) {
Wei Li9b761132016-01-29 15:44:20 -0800819 FX_FLOAT c = pEntry->GetNumberAt(0);
820 FX_FLOAT m = pEntry->GetNumberAt(1);
821 FX_FLOAT y = pEntry->GetNumberAt(2);
822 FX_FLOAT k = pEntry->GetNumberAt(3);
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700823
Lei Zhang375a8642016-01-11 11:59:17 -0800824 FX_FLOAT r = 1.0f - std::min(1.0f, c + k);
825 FX_FLOAT g = 1.0f - std::min(1.0f, m + k);
826 FX_FLOAT b = 1.0f - std::min(1.0f, y + k);
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700827
828 color = FXSYS_RGB((int)(r * 255), (int)(g * 255), (int)(b * 255));
829
830 return TRUE;
831 }
832 }
833
834 return FALSE;
835}
836
837void CPDFSDK_BAAnnot::WriteAppearance(const CFX_ByteString& sAPType,
838 const CPDF_Rect& rcBBox,
Tom Sepez60d909e2015-12-10 15:34:55 -0800839 const CFX_Matrix& matrix,
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700840 const CFX_ByteString& sContents,
841 const CFX_ByteString& sAPState) {
Wei Li9b761132016-01-29 15:44:20 -0800842 CPDF_Dictionary* pAPDict = m_pAnnot->GetAnnotDict()->GetDictBy("AP");
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700843
844 if (!pAPDict) {
845 pAPDict = new CPDF_Dictionary;
846 m_pAnnot->GetAnnotDict()->SetAt("AP", pAPDict);
847 }
848
Dan Sinclairbfe042a2015-11-04 14:04:13 -0500849 CPDF_Stream* pStream = nullptr;
850 CPDF_Dictionary* pParentDict = nullptr;
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700851
852 if (sAPState.IsEmpty()) {
853 pParentDict = pAPDict;
Wei Li9b761132016-01-29 15:44:20 -0800854 pStream = pAPDict->GetStreamBy(sAPType);
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700855 } else {
Wei Li9b761132016-01-29 15:44:20 -0800856 CPDF_Dictionary* pAPTypeDict = pAPDict->GetDictBy(sAPType);
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700857 if (!pAPTypeDict) {
Tom Sepezae51c812015-08-05 12:34:06 -0700858 pAPTypeDict = new CPDF_Dictionary;
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700859 pAPDict->SetAt(sAPType, pAPTypeDict);
Tom Sepez2f2ffec2015-07-23 14:42:09 -0700860 }
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700861
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700862 pParentDict = pAPTypeDict;
Wei Li9b761132016-01-29 15:44:20 -0800863 pStream = pAPTypeDict->GetStreamBy(sAPState);
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700864 }
865
866 if (!pStream) {
Dan Sinclairbfe042a2015-11-04 14:04:13 -0500867 pStream = new CPDF_Stream(nullptr, 0, nullptr);
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700868
Dan Sinclairbfe042a2015-11-04 14:04:13 -0500869 CPDF_Document* pDoc = m_pPageView->GetPDFDocument();
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700870 int32_t objnum = pDoc->AddIndirectObject(pStream);
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700871 pParentDict->SetAtReference(sAPType, pDoc, objnum);
872 }
873
874 CPDF_Dictionary* pStreamDict = pStream->GetDict();
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700875 if (!pStreamDict) {
Tom Sepezae51c812015-08-05 12:34:06 -0700876 pStreamDict = new CPDF_Dictionary;
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700877 pStreamDict->SetAtName("Type", "XObject");
878 pStreamDict->SetAtName("Subtype", "Form");
879 pStreamDict->SetAtInteger("FormType", 1);
Dan Sinclairbfe042a2015-11-04 14:04:13 -0500880 pStream->InitStream(nullptr, 0, pStreamDict);
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700881 }
882
883 if (pStreamDict) {
884 pStreamDict->SetAtMatrix("Matrix", matrix);
885 pStreamDict->SetAtRect("BBox", rcBBox);
886 }
887
888 pStream->SetData((uint8_t*)sContents.c_str(), sContents.GetLength(), FALSE,
889 FALSE);
890}
891
892#define BA_ANNOT_MINWIDTH 1
893#define BA_ANNOT_MINHEIGHT 1
894
895FX_FLOAT CPDFSDK_Annot::GetMinWidth() const {
896 return BA_ANNOT_MINWIDTH;
897}
898
899FX_FLOAT CPDFSDK_Annot::GetMinHeight() const {
900 return BA_ANNOT_MINHEIGHT;
901}
902
903FX_BOOL CPDFSDK_BAAnnot::CreateFormFiller() {
904 return TRUE;
905}
906FX_BOOL CPDFSDK_BAAnnot::IsVisible() const {
907 int nFlags = GetFlags();
908 return !((nFlags & ANNOTFLAG_INVISIBLE) || (nFlags & ANNOTFLAG_HIDDEN) ||
909 (nFlags & ANNOTFLAG_NOVIEW));
910}
911
912CPDF_Action CPDFSDK_BAAnnot::GetAction() const {
Wei Li9b761132016-01-29 15:44:20 -0800913 return CPDF_Action(m_pAnnot->GetAnnotDict()->GetDictBy("A"));
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700914}
915
916void CPDFSDK_BAAnnot::SetAction(const CPDF_Action& action) {
917 ASSERT(action);
918 if ((CPDF_Action&)action !=
Wei Li9b761132016-01-29 15:44:20 -0800919 CPDF_Action(m_pAnnot->GetAnnotDict()->GetDictBy("A"))) {
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700920 CPDF_Document* pDoc = m_pPageView->GetPDFDocument();
921 CPDF_Dictionary* pDict = action.GetDict();
922 if (pDict && pDict->GetObjNum() == 0) {
923 pDoc->AddIndirectObject(pDict);
Tom Sepez2f2ffec2015-07-23 14:42:09 -0700924 }
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700925 m_pAnnot->GetAnnotDict()->SetAtReference("A", pDoc, pDict->GetObjNum());
926 }
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700927}
928
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700929void CPDFSDK_BAAnnot::RemoveAction() {
930 m_pAnnot->GetAnnotDict()->RemoveAt("A");
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700931}
932
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700933CPDF_AAction CPDFSDK_BAAnnot::GetAAction() const {
Wei Li9b761132016-01-29 15:44:20 -0800934 return m_pAnnot->GetAnnotDict()->GetDictBy("AA");
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700935}
936
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700937void CPDFSDK_BAAnnot::SetAAction(const CPDF_AAction& aa) {
Wei Li9b761132016-01-29 15:44:20 -0800938 if ((CPDF_AAction&)aa != m_pAnnot->GetAnnotDict()->GetDictBy("AA"))
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700939 m_pAnnot->GetAnnotDict()->SetAt("AA", (CPDF_AAction&)aa);
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700940}
941
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700942void CPDFSDK_BAAnnot::RemoveAAction() {
943 m_pAnnot->GetAnnotDict()->RemoveAt("AA");
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700944}
945
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700946CPDF_Action CPDFSDK_BAAnnot::GetAAction(CPDF_AAction::AActionType eAAT) {
947 CPDF_AAction AAction = GetAAction();
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700948
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700949 if (AAction.ActionExist(eAAT))
950 return AAction.GetAction(eAAT);
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700951
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700952 if (eAAT == CPDF_AAction::ButtonUp)
953 return GetAction();
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700954
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700955 return CPDF_Action();
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700956}
957
Tom Sepez51da0932015-11-25 16:05:49 -0800958#ifdef PDF_ENABLE_XFA
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700959FX_BOOL CPDFSDK_BAAnnot::IsXFAField() {
960 return FALSE;
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700961}
Tom Sepez40e9ff32015-11-30 12:39:54 -0800962#endif // PDF_ENABLE_XFA
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700963
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700964void CPDFSDK_BAAnnot::Annot_OnDraw(CFX_RenderDevice* pDevice,
Tom Sepez60d909e2015-12-10 15:34:55 -0800965 CFX_Matrix* pUser2Device,
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700966 CPDF_RenderOptions* pOptions) {
967 m_pAnnot->GetAPForm(m_pPageView->GetPDFPage(), CPDF_Annot::Normal);
968 m_pAnnot->DrawAppearance(m_pPageView->GetPDFPage(), pDevice, pUser2Device,
969 CPDF_Annot::Normal, NULL);
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700970}
971
Tom Sepez50d12ad2015-11-24 09:50:51 -0800972UnderlyingPageType* CPDFSDK_Annot::GetUnderlyingPage() {
Tom Sepez40e9ff32015-11-30 12:39:54 -0800973#ifdef PDF_ENABLE_XFA
Tom Sepez50d12ad2015-11-24 09:50:51 -0800974 return GetPDFXFAPage();
Tom Sepez40e9ff32015-11-30 12:39:54 -0800975#else // PDF_ENABLE_XFA
976 return GetPDFPage();
977#endif // PDF_ENABLE_XFA
Tom Sepez50d12ad2015-11-24 09:50:51 -0800978}
979
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700980CPDF_Page* CPDFSDK_Annot::GetPDFPage() {
Lei Zhang05e67412016-01-25 16:35:42 -0800981 return m_pPageView ? m_pPageView->GetPDFPage() : nullptr;
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700982}
983
Tom Sepez40e9ff32015-11-30 12:39:54 -0800984#ifdef PDF_ENABLE_XFA
Nico Weber9d8ec5a2015-08-04 13:00:21 -0700985CPDFXFA_Page* CPDFSDK_Annot::GetPDFXFAPage() {
Lei Zhang05e67412016-01-25 16:35:42 -0800986 return m_pPageView ? m_pPageView->GetPDFXFAPage() : nullptr;
John Abd-El-Malek3f3b45c2014-05-23 17:28:10 -0700987}
Tom Sepez40e9ff32015-11-30 12:39:54 -0800988#endif // PDF_ENABLE_XFA