1// 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 <algorithm>
8#include <memory>
9
10#include "fpdfsdk/include/fsdk_mgr.h"
11
12#include "fpdfsdk/include/formfiller/FFL_FormFiller.h"
13#include "fpdfsdk/include/fsdk_define.h"
14#include "fpdfsdk/include/javascript/IJavaScript.h"
15#include "public/fpdf_ext.h"
16#include "third_party/base/stl_util.h"
17
18#ifdef PDF_ENABLE_XFA
19#include "fpdfsdk/include/fpdfxfa/fpdfxfa_app.h"
20#include "fpdfsdk/include/fpdfxfa/fpdfxfa_doc.h"
21#include "fpdfsdk/include/fpdfxfa/fpdfxfa_page.h"
22#include "fpdfsdk/include/fpdfxfa/fpdfxfa_util.h"
23#endif  // PDF_ENABLE_XFA
24
25#if _FX_OS_ == _FX_ANDROID_
26#include "time.h"
27#else
28#include <ctime>
29#endif
30
31class CFX_SystemHandler : public IFX_SystemHandler {
32 public:
33  explicit CFX_SystemHandler(CPDFDoc_Environment* pEnv)
34      : m_pEnv(pEnv), m_nCharSet(-1) {}
35  ~CFX_SystemHandler() override {}
36
37 public:
38  // IFX_SystemHandler
39  void InvalidateRect(FX_HWND hWnd, FX_RECT rect) override;
40  void OutputSelectedRect(void* pFormFiller, CPDF_Rect& rect) override;
41  FX_BOOL IsSelectionImplemented() override;
42  CFX_WideString GetClipboardText(FX_HWND hWnd) override { return L""; }
43  FX_BOOL SetClipboardText(FX_HWND hWnd, CFX_WideString string) override {
44    return FALSE;
45  }
46  void ClientToScreen(FX_HWND hWnd, int32_t& x, int32_t& y) override {}
47  void ScreenToClient(FX_HWND hWnd, int32_t& x, int32_t& y) override {}
48  void SetCursor(int32_t nCursorType) override;
49  FX_HMENU CreatePopupMenu() override { return NULL; }
50  FX_BOOL AppendMenuItem(FX_HMENU hMenu,
51                         int32_t nIDNewItem,
52                         CFX_WideString string) override {
53    return FALSE;
54  }
55  FX_BOOL EnableMenuItem(FX_HMENU hMenu,
56                         int32_t nIDItem,
57                         FX_BOOL bEnabled) override {
58    return FALSE;
59  }
60  int32_t TrackPopupMenu(FX_HMENU hMenu,
61                         int32_t x,
62                         int32_t y,
63                         FX_HWND hParent) override {
64    return -1;
65  }
66  void DestroyMenu(FX_HMENU hMenu) override {}
67  CFX_ByteString GetNativeTrueTypeFont(int32_t nCharset) override;
68  FX_BOOL FindNativeTrueTypeFont(int32_t nCharset,
69                                 CFX_ByteString sFontFaceName) override;
70  CPDF_Font* AddNativeTrueTypeFontToPDF(CPDF_Document* pDoc,
71                                        CFX_ByteString sFontFaceName,
72                                        uint8_t nCharset) override;
73  int32_t SetTimer(int32_t uElapse, TimerCallback lpTimerFunc) override;
74  void KillTimer(int32_t nID) override;
75  FX_BOOL IsSHIFTKeyDown(FX_DWORD nFlag) override {
76    return m_pEnv->FFI_IsSHIFTKeyDown(nFlag);
77  }
78  FX_BOOL IsCTRLKeyDown(FX_DWORD nFlag) override {
79    return m_pEnv->FFI_IsCTRLKeyDown(nFlag);
80  }
81  FX_BOOL IsALTKeyDown(FX_DWORD nFlag) override {
82    return m_pEnv->FFI_IsALTKeyDown(nFlag);
83  }
84  FX_BOOL IsINSERTKeyDown(FX_DWORD nFlag) override {
85    return m_pEnv->FFI_IsINSERTKeyDown(nFlag);
86  }
87  FX_SYSTEMTIME GetLocalTime() override;
88  int32_t GetCharSet() override { return m_nCharSet; }
89  void SetCharSet(int32_t nCharSet) override { m_nCharSet = nCharSet; }
90
91 private:
92  CPDFDoc_Environment* m_pEnv;
93  int m_nCharSet;
94};
95
96void CFX_SystemHandler::SetCursor(int32_t nCursorType) {
97  m_pEnv->FFI_SetCursor(nCursorType);
98}
99
100void CFX_SystemHandler::InvalidateRect(FX_HWND hWnd, FX_RECT rect) {
101  CPDFSDK_Annot* pSDKAnnot = (CPDFSDK_Annot*)hWnd;
102  CPDFSDK_PageView* pPageView = pSDKAnnot->GetPageView();
103  UnderlyingPageType* pPage = pSDKAnnot->GetUnderlyingPage();
104  if (!pPage || !pPageView)
105    return;
106  CFX_Matrix page2device;
107  pPageView->GetCurrentMatrix(page2device);
108  CFX_Matrix device2page;
109  device2page.SetReverse(page2device);
110  FX_FLOAT left, top, right, bottom;
111  device2page.Transform((FX_FLOAT)rect.left, (FX_FLOAT)rect.top, left, top);
112  device2page.Transform((FX_FLOAT)rect.right, (FX_FLOAT)rect.bottom, right,
113                        bottom);
114  CPDF_Rect rcPDF(left, bottom, right, top);
115  rcPDF.Normalize();
116
117  m_pEnv->FFI_Invalidate(pPage, rcPDF.left, rcPDF.top, rcPDF.right,
118                         rcPDF.bottom);
119}
120void CFX_SystemHandler::OutputSelectedRect(void* pFormFiller, CPDF_Rect& rect) {
121  CFFL_FormFiller* pFFL = (CFFL_FormFiller*)pFormFiller;
122  if (pFFL) {
123    CPDF_Point leftbottom = CPDF_Point(rect.left, rect.bottom);
124    CPDF_Point righttop = CPDF_Point(rect.right, rect.top);
125    CPDF_Point ptA = pFFL->PWLtoFFL(leftbottom);
126    CPDF_Point ptB = pFFL->PWLtoFFL(righttop);
127    CPDFSDK_Annot* pAnnot = pFFL->GetSDKAnnot();
128    UnderlyingPageType* pPage = pAnnot->GetUnderlyingPage();
129    ASSERT(pPage);
130    m_pEnv->FFI_OutputSelectedRect(pPage, ptA.x, ptB.y, ptB.x, ptA.y);
131  }
132}
133
134FX_BOOL CFX_SystemHandler::IsSelectionImplemented() {
135  if (m_pEnv) {
136    FPDF_FORMFILLINFO* pInfo = m_pEnv->GetFormFillInfo();
137    if (pInfo && pInfo->FFI_OutputSelectedRect)
138      return TRUE;
139  }
140  return FALSE;
141}
142
143CFX_ByteString CFX_SystemHandler::GetNativeTrueTypeFont(int32_t nCharset) {
144  return "";
145}
146
147FX_BOOL CFX_SystemHandler::FindNativeTrueTypeFont(
148    int32_t nCharset,
149    CFX_ByteString sFontFaceName) {
150  CFX_FontMgr* pFontMgr = CFX_GEModule::Get()->GetFontMgr();
151  if (!pFontMgr)
152    return FALSE;
153
154  CFX_FontMapper* pFontMapper = pFontMgr->GetBuiltinMapper();
155  if (!pFontMapper)
156    return FALSE;
157
158  int nSize = pFontMapper->m_InstalledTTFonts.GetSize();
159  if (nSize == 0) {
160    pFontMapper->LoadInstalledFonts();
161    nSize = pFontMapper->m_InstalledTTFonts.GetSize();
162  }
163
164  for (int i = 0; i < nSize; ++i) {
165    if (pFontMapper->m_InstalledTTFonts[i].Compare(sFontFaceName))
166      return TRUE;
167  }
168
169  return FALSE;
170}
171
172static int CharSet2CP(int charset) {
173  if (charset == 128)
174    return 932;
175  if (charset == 134)
176    return 936;
177  if (charset == 129)
178    return 949;
179  if (charset == 136)
180    return 950;
181  return 0;
182}
183CPDF_Font* CFX_SystemHandler::AddNativeTrueTypeFontToPDF(
184    CPDF_Document* pDoc,
185    CFX_ByteString sFontFaceName,
186    uint8_t nCharset) {
187  if (pDoc) {
188    CFX_Font* pFXFont = new CFX_Font();
189    pFXFont->LoadSubst(sFontFaceName, TRUE, 0, 0, 0, CharSet2CP(nCharset),
190                       FALSE);
191    CPDF_Font* pFont = pDoc->AddFont(pFXFont, nCharset, FALSE);
192    delete pFXFont;
193    return pFont;
194  }
195
196  return NULL;
197}
198
199int32_t CFX_SystemHandler::SetTimer(int32_t uElapse,
200                                    TimerCallback lpTimerFunc) {
201  return m_pEnv->FFI_SetTimer(uElapse, lpTimerFunc);
202}
203void CFX_SystemHandler::KillTimer(int32_t nID) {
204  m_pEnv->FFI_KillTimer(nID);
205}
206
207FX_SYSTEMTIME CFX_SystemHandler::GetLocalTime() {
208  return m_pEnv->FFI_GetLocalTime();
209}
210
211CPDFDoc_Environment::CPDFDoc_Environment(UnderlyingDocumentType* pDoc,
212                                         FPDF_FORMFILLINFO* pFFinfo)
213    : m_pInfo(pFFinfo), m_pSDKDoc(NULL), m_pUnderlyingDoc(pDoc) {
214  m_pSysHandler.reset(new CFX_SystemHandler(this));
215}
216
217CPDFDoc_Environment::~CPDFDoc_Environment() {
218#ifdef PDF_ENABLE_XFA
219  CPDFXFA_App* pProvider = CPDFXFA_App::GetInstance();
220  if (pProvider->m_pEnvList.GetSize() == 0)
221    pProvider->SetJavaScriptInitialized(FALSE);
222#endif  // PDF_ENABLE_XFA
223}
224
225int CPDFDoc_Environment::JS_appAlert(const FX_WCHAR* Msg,
226                                     const FX_WCHAR* Title,
227                                     FX_UINT Type,
228                                     FX_UINT Icon) {
229  if (m_pInfo && m_pInfo->m_pJsPlatform && m_pInfo->m_pJsPlatform->app_alert) {
230    CFX_ByteString bsMsg = CFX_WideString(Msg).UTF16LE_Encode();
231    CFX_ByteString bsTitle = CFX_WideString(Title).UTF16LE_Encode();
232    FPDF_WIDESTRING pMsg = (FPDF_WIDESTRING)bsMsg.GetBuffer(bsMsg.GetLength());
233    FPDF_WIDESTRING pTitle =
234        (FPDF_WIDESTRING)bsTitle.GetBuffer(bsTitle.GetLength());
235    int ret = m_pInfo->m_pJsPlatform->app_alert(m_pInfo->m_pJsPlatform, pMsg,
236                                                pTitle, Type, Icon);
237    bsMsg.ReleaseBuffer();
238    bsTitle.ReleaseBuffer();
239    return ret;
240  }
241  return -1;
242}
243
244int CPDFDoc_Environment::JS_appResponse(const FX_WCHAR* Question,
245                                        const FX_WCHAR* Title,
246                                        const FX_WCHAR* Default,
247                                        const FX_WCHAR* cLabel,
248                                        FPDF_BOOL bPassword,
249                                        void* response,
250                                        int length) {
251  if (m_pInfo && m_pInfo->m_pJsPlatform &&
252      m_pInfo->m_pJsPlatform->app_response) {
253    CFX_ByteString bsQuestion = CFX_WideString(Question).UTF16LE_Encode();
254    CFX_ByteString bsTitle = CFX_WideString(Title).UTF16LE_Encode();
255    CFX_ByteString bsDefault = CFX_WideString(Default).UTF16LE_Encode();
256    CFX_ByteString bsLabel = CFX_WideString(cLabel).UTF16LE_Encode();
257    FPDF_WIDESTRING pQuestion =
258        (FPDF_WIDESTRING)bsQuestion.GetBuffer(bsQuestion.GetLength());
259    FPDF_WIDESTRING pTitle =
260        (FPDF_WIDESTRING)bsTitle.GetBuffer(bsTitle.GetLength());
261    FPDF_WIDESTRING pDefault =
262        (FPDF_WIDESTRING)bsDefault.GetBuffer(bsDefault.GetLength());
263    FPDF_WIDESTRING pLabel =
264        (FPDF_WIDESTRING)bsLabel.GetBuffer(bsLabel.GetLength());
265    int ret = m_pInfo->m_pJsPlatform->app_response(
266        m_pInfo->m_pJsPlatform, pQuestion, pTitle, pDefault, pLabel, bPassword,
267        response, length);
268    bsQuestion.ReleaseBuffer();
269    bsTitle.ReleaseBuffer();
270    bsDefault.ReleaseBuffer();
271    bsLabel.ReleaseBuffer();
272    return ret;
273  }
274  return -1;
275}
276
277CFX_WideString CPDFDoc_Environment::JS_fieldBrowse() {
278  if (!m_pInfo || !m_pInfo->m_pJsPlatform ||
279      !m_pInfo->m_pJsPlatform->Field_browse) {
280    return L"";
281  }
282
283  const int nRequiredLen =
284      m_pInfo->m_pJsPlatform->Field_browse(m_pInfo->m_pJsPlatform, nullptr, 0);
285  if (nRequiredLen <= 0)
286    return L"";
287
288  std::unique_ptr<char[]> pBuff(new char[nRequiredLen]);
289  memset(pBuff.get(), 0, nRequiredLen);
290  const int nActualLen = m_pInfo->m_pJsPlatform->Field_browse(
291      m_pInfo->m_pJsPlatform, pBuff.get(), nRequiredLen);
292  if (nActualLen <= 0 || nActualLen > nRequiredLen)
293    return L"";
294
295  CFX_ByteString bsRet = CFX_ByteString(pBuff.get(), nActualLen);
296  CFX_WideString wsRet = CFX_WideString::FromLocal(bsRet);
297  return wsRet;
298}
299
300CFX_WideString CPDFDoc_Environment::JS_docGetFilePath() {
301  if (!m_pInfo || !m_pInfo->m_pJsPlatform ||
302      !m_pInfo->m_pJsPlatform->Doc_getFilePath) {
303    return L"";
304  }
305
306  const int nRequiredLen = m_pInfo->m_pJsPlatform->Doc_getFilePath(
307      m_pInfo->m_pJsPlatform, nullptr, 0);
308  if (nRequiredLen <= 0)
309    return L"";
310
311  std::unique_ptr<char[]> pBuff(new char[nRequiredLen]);
312  memset(pBuff.get(), 0, nRequiredLen);
313  const int nActualLen = m_pInfo->m_pJsPlatform->Doc_getFilePath(
314      m_pInfo->m_pJsPlatform, pBuff.get(), nRequiredLen);
315  if (nActualLen <= 0 || nActualLen > nRequiredLen)
316    return L"";
317
318  CFX_ByteString bsRet = CFX_ByteString(pBuff.get(), nActualLen);
319  CFX_WideString wsRet = CFX_WideString::FromLocal(bsRet);
320  return wsRet;
321}
322
323void CPDFDoc_Environment::JS_docSubmitForm(void* formData,
324                                           int length,
325                                           const FX_WCHAR* URL) {
326  if (m_pInfo && m_pInfo->m_pJsPlatform &&
327      m_pInfo->m_pJsPlatform->Doc_submitForm) {
328    CFX_ByteString bsDestination = CFX_WideString(URL).UTF16LE_Encode();
329    FPDF_WIDESTRING pDestination =
330        (FPDF_WIDESTRING)bsDestination.GetBuffer(bsDestination.GetLength());
331    m_pInfo->m_pJsPlatform->Doc_submitForm(m_pInfo->m_pJsPlatform, formData,
332                                           length, pDestination);
333    bsDestination.ReleaseBuffer();
334  }
335}
336
337void CPDFDoc_Environment::JS_docmailForm(void* mailData,
338                                         int length,
339                                         FPDF_BOOL bUI,
340                                         const FX_WCHAR* To,
341                                         const FX_WCHAR* Subject,
342                                         const FX_WCHAR* CC,
343                                         const FX_WCHAR* BCC,
344                                         const FX_WCHAR* Msg) {
345  if (m_pInfo && m_pInfo->m_pJsPlatform && m_pInfo->m_pJsPlatform->Doc_mail) {
346    CFX_ByteString bsTo = CFX_WideString(To).UTF16LE_Encode();
347    CFX_ByteString bsCC = CFX_WideString(Subject).UTF16LE_Encode();
348    CFX_ByteString bsBcc = CFX_WideString(BCC).UTF16LE_Encode();
349    CFX_ByteString bsSubject = CFX_WideString(Subject).UTF16LE_Encode();
350    CFX_ByteString bsMsg = CFX_WideString(Msg).UTF16LE_Encode();
351    FPDF_WIDESTRING pTo = (FPDF_WIDESTRING)bsTo.GetBuffer(bsTo.GetLength());
352    FPDF_WIDESTRING pCC = (FPDF_WIDESTRING)bsCC.GetBuffer(bsCC.GetLength());
353    FPDF_WIDESTRING pBcc = (FPDF_WIDESTRING)bsBcc.GetBuffer(bsBcc.GetLength());
354    FPDF_WIDESTRING pSubject =
355        (FPDF_WIDESTRING)bsSubject.GetBuffer(bsSubject.GetLength());
356    FPDF_WIDESTRING pMsg = (FPDF_WIDESTRING)bsMsg.GetBuffer(bsMsg.GetLength());
357    m_pInfo->m_pJsPlatform->Doc_mail(m_pInfo->m_pJsPlatform, mailData, length,
358                                     bUI, pTo, pSubject, pCC, pBcc, pMsg);
359    bsTo.ReleaseBuffer();
360    bsCC.ReleaseBuffer();
361    bsBcc.ReleaseBuffer();
362    bsSubject.ReleaseBuffer();
363    bsMsg.ReleaseBuffer();
364  }
365}
366
367IJS_Runtime* CPDFDoc_Environment::GetJSRuntime() {
368  if (!IsJSInitiated())
369    return NULL;
370  if (!m_pJSRuntime)
371    m_pJSRuntime.reset(IJS_Runtime::Create(this));
372  return m_pJSRuntime.get();
373}
374
375CPDFSDK_AnnotHandlerMgr* CPDFDoc_Environment::GetAnnotHandlerMgr() {
376  if (!m_pAnnotHandlerMgr)
377    m_pAnnotHandlerMgr.reset(new CPDFSDK_AnnotHandlerMgr(this));
378  return m_pAnnotHandlerMgr.get();
379}
380
381CPDFSDK_ActionHandler* CPDFDoc_Environment::GetActionHander() {
382  if (!m_pActionHandler)
383    m_pActionHandler.reset(new CPDFSDK_ActionHandler());
384  return m_pActionHandler.get();
385}
386
387CFFL_IFormFiller* CPDFDoc_Environment::GetIFormFiller() {
388  if (!m_pIFormFiller)
389    m_pIFormFiller.reset(new CFFL_IFormFiller(this));
390  return m_pIFormFiller.get();
391}
392
393CPDFSDK_Document::CPDFSDK_Document(UnderlyingDocumentType* pDoc,
394                                   CPDFDoc_Environment* pEnv)
395    : m_pDoc(pDoc),
396      m_pFocusAnnot(nullptr),
397      m_pEnv(pEnv),
398      m_bChangeMask(FALSE),
399      m_bBeingDestroyed(FALSE) {}
400
401CPDFSDK_Document::~CPDFSDK_Document() {
402  m_bBeingDestroyed = TRUE;
403
404  for (auto& it : m_pageMap)
405    it.second->KillFocusAnnotIfNeeded();
406
407  for (auto& it : m_pageMap)
408    delete it.second;
409  m_pageMap.clear();
410}
411
412CPDFSDK_PageView* CPDFSDK_Document::GetPageView(
413    UnderlyingPageType* pUnderlyingPage,
414    FX_BOOL ReNew) {
415  auto it = m_pageMap.find(pUnderlyingPage);
416  if (it != m_pageMap.end())
417    return it->second;
418
419  if (!ReNew)
420    return nullptr;
421
422  CPDFSDK_PageView* pPageView = new CPDFSDK_PageView(this, pUnderlyingPage);
423  m_pageMap[pUnderlyingPage] = pPageView;
424  // Delay to load all the annotations, to avoid endless loop.
425  pPageView->LoadFXAnnots();
426  return pPageView;
427}
428
429CPDFSDK_PageView* CPDFSDK_Document::GetCurrentView() {
430  UnderlyingPageType* pPage =
431      UnderlyingFromFPDFPage(m_pEnv->FFI_GetCurrentPage(m_pDoc));
432  return pPage ? GetPageView(pPage, TRUE) : nullptr;
433}
434
435CPDFSDK_PageView* CPDFSDK_Document::GetPageView(int nIndex) {
436  UnderlyingPageType* pTempPage =
437      UnderlyingFromFPDFPage(m_pEnv->FFI_GetPage(m_pDoc, nIndex));
438  if (!pTempPage)
439    return nullptr;
440
441  auto it = m_pageMap.find(pTempPage);
442  return it->second;
443}
444
445void CPDFSDK_Document::ProcJavascriptFun() {
446  CPDF_Document* pPDFDoc = GetPDFDocument();
447  CPDF_DocJSActions docJS(pPDFDoc);
448  int iCount = docJS.CountJSActions();
449  if (iCount < 1)
450    return;
451  for (int i = 0; i < iCount; i++) {
452    CFX_ByteString csJSName;
453    CPDF_Action jsAction = docJS.GetJSAction(i, csJSName);
454    if (m_pEnv->GetActionHander())
455      m_pEnv->GetActionHander()->DoAction_JavaScript(
456          jsAction, CFX_WideString::FromLocal(csJSName), this);
457  }
458}
459
460FX_BOOL CPDFSDK_Document::ProcOpenAction() {
461  if (!m_pDoc)
462    return FALSE;
463
464  CPDF_Dictionary* pRoot = GetPDFDocument()->GetRoot();
465  if (!pRoot)
466    return FALSE;
467
468  CPDF_Object* pOpenAction = pRoot->GetDict("OpenAction");
469  if (!pOpenAction)
470    pOpenAction = pRoot->GetArray("OpenAction");
471
472  if (!pOpenAction)
473    return FALSE;
474
475  if (pOpenAction->IsArray())
476    return TRUE;
477
478  if (CPDF_Dictionary* pDict = pOpenAction->AsDictionary()) {
479    CPDF_Action action(pDict);
480    if (m_pEnv->GetActionHander())
481      m_pEnv->GetActionHander()->DoAction_DocOpen(action, this);
482    return TRUE;
483  }
484  return FALSE;
485}
486
487CPDF_OCContext* CPDFSDK_Document::GetOCContext() {
488  if (!m_pOccontent)
489    m_pOccontent.reset(new CPDF_OCContext(GetPDFDocument()));
490  return m_pOccontent.get();
491}
492
493void CPDFSDK_Document::RemovePageView(UnderlyingPageType* pUnderlyingPage) {
494  auto it = m_pageMap.find(pUnderlyingPage);
495  if (it == m_pageMap.end())
496    return;
497
498  CPDFSDK_PageView* pPageView = it->second;
499  if (pPageView->IsLocked())
500    return;
501
502  pPageView->KillFocusAnnotIfNeeded();
503  delete pPageView;
504  m_pageMap.erase(it);
505}
506
507UnderlyingPageType* CPDFSDK_Document::GetPage(int nIndex) {
508  return UnderlyingFromFPDFPage(m_pEnv->FFI_GetPage(m_pDoc, nIndex));
509}
510
511CPDFSDK_InterForm* CPDFSDK_Document::GetInterForm() {
512  if (!m_pInterForm)
513    m_pInterForm.reset(new CPDFSDK_InterForm(this));
514  return m_pInterForm.get();
515}
516
517void CPDFSDK_Document::UpdateAllViews(CPDFSDK_PageView* pSender,
518                                      CPDFSDK_Annot* pAnnot) {
519  for (const auto& it : m_pageMap) {
520    CPDFSDK_PageView* pPageView = it.second;
521    if (pPageView != pSender) {
522      pPageView->UpdateView(pAnnot);
523    }
524  }
525}
526
527CPDFSDK_Annot* CPDFSDK_Document::GetFocusAnnot() {
528  return m_pFocusAnnot;
529}
530
531FX_BOOL CPDFSDK_Document::SetFocusAnnot(CPDFSDK_Annot* pAnnot, FX_UINT nFlag) {
532  if (m_bBeingDestroyed)
533    return FALSE;
534
535  if (m_pFocusAnnot == pAnnot)
536    return TRUE;
537
538  if (m_pFocusAnnot) {
539    if (!KillFocusAnnot(nFlag))
540      return FALSE;
541  }
542
543  if (!pAnnot)
544    return FALSE;
545
546#ifdef PDF_ENABLE_XFA
547  CPDFSDK_Annot* pLastFocusAnnot = m_pFocusAnnot;
548#endif  // PDF_ENABLE_XFA
549  CPDFSDK_PageView* pPageView = pAnnot->GetPageView();
550  if (pPageView && pPageView->IsValid()) {
551    CPDFSDK_AnnotHandlerMgr* pAnnotHandler = m_pEnv->GetAnnotHandlerMgr();
552    if (!m_pFocusAnnot) {
553#ifdef PDF_ENABLE_XFA
554      if (!pAnnotHandler->Annot_OnChangeFocus(pAnnot, pLastFocusAnnot))
555        return FALSE;
556#endif  // PDF_ENABLE_XFA
557      if (!pAnnotHandler->Annot_OnSetFocus(pAnnot, nFlag))
558        return FALSE;
559      if (!m_pFocusAnnot) {
560        m_pFocusAnnot = pAnnot;
561        return TRUE;
562      }
563    }
564  }
565  return FALSE;
566}
567
568FX_BOOL CPDFSDK_Document::KillFocusAnnot(FX_UINT nFlag) {
569  if (m_pFocusAnnot) {
570    CPDFSDK_AnnotHandlerMgr* pAnnotHandler = m_pEnv->GetAnnotHandlerMgr();
571    CPDFSDK_Annot* pFocusAnnot = m_pFocusAnnot;
572    m_pFocusAnnot = nullptr;
573
574#ifdef PDF_ENABLE_XFA
575    if (!pAnnotHandler->Annot_OnChangeFocus(nullptr, pFocusAnnot))
576      return FALSE;
577#endif  // PDF_ENABLE_XFA
578
579    if (pAnnotHandler->Annot_OnKillFocus(pFocusAnnot, nFlag)) {
580      if (pFocusAnnot->GetType() == "Widget") {
581        CPDFSDK_Widget* pWidget = (CPDFSDK_Widget*)pFocusAnnot;
582        int nFieldType = pWidget->GetFieldType();
583        if (FIELDTYPE_TEXTFIELD == nFieldType ||
584            FIELDTYPE_COMBOBOX == nFieldType) {
585          m_pEnv->FFI_OnSetFieldInputFocus(NULL, NULL, 0, FALSE);
586        }
587      }
588
589      if (!m_pFocusAnnot)
590        return TRUE;
591    } else {
592      m_pFocusAnnot = pFocusAnnot;
593    }
594  }
595  return FALSE;
596}
597
598void CPDFSDK_Document::OnCloseDocument() {
599  KillFocusAnnot();
600}
601
602FX_BOOL CPDFSDK_Document::GetPermissions(int nFlag) {
603  return GetPDFDocument()->GetUserPermissions() & nFlag;
604}
605
606IJS_Runtime* CPDFSDK_Document::GetJsRuntime() {
607  return m_pEnv->GetJSRuntime();
608}
609
610CFX_WideString CPDFSDK_Document::GetPath() {
611  return m_pEnv->JS_docGetFilePath();
612}
613
614CPDFSDK_PageView::CPDFSDK_PageView(CPDFSDK_Document* pSDKDoc,
615                                   UnderlyingPageType* page)
616    : m_page(page),
617      m_pSDKDoc(pSDKDoc),
618      m_CaptureWidget(nullptr),
619#ifndef PDF_ENABLE_XFA
620      m_bTakeOverPage(FALSE),
621#endif  // PDF_ENABLE_XFA
622      m_bEnterWidget(FALSE),
623      m_bExitWidget(FALSE),
624      m_bOnWidget(FALSE),
625      m_bValid(FALSE),
626      m_bLocked(FALSE) {
627  CPDFSDK_InterForm* pInterForm = pSDKDoc->GetInterForm();
628  if (pInterForm) {
629    CPDF_InterForm* pPDFInterForm = pInterForm->GetInterForm();
630#ifdef PDF_ENABLE_XFA
631    if (page->GetPDFPage())
632      pPDFInterForm->FixPageFields(page->GetPDFPage());
633#else   // PDF_ENABLE_XFA
634    pPDFInterForm->FixPageFields(page);
635#endif  // PDF_ENABLE_XFA
636  }
637#ifndef PDF_ENABLE_XFA
638  m_page->SetPrivateData((void*)m_page, (void*)this, nullptr);
639#endif  // PDF_ENABLE_XFA
640}
641
642CPDFSDK_PageView::~CPDFSDK_PageView() {
643  CPDFDoc_Environment* pEnv = m_pSDKDoc->GetEnv();
644  CPDFSDK_AnnotHandlerMgr* pAnnotHandlerMgr = pEnv->GetAnnotHandlerMgr();
645  for (CPDFSDK_Annot* pAnnot : m_fxAnnotArray)
646    pAnnotHandlerMgr->ReleaseAnnot(pAnnot);
647
648  m_fxAnnotArray.clear();
649  m_pAnnotList.reset();
650#ifndef PDF_ENABLE_XFA
651  m_page->RemovePrivateData((void*)m_page);
652  if (m_bTakeOverPage) {
653    delete m_page;
654  }
655#endif  // PDF_ENABLE_XFA
656}
657
658void CPDFSDK_PageView::PageView_OnDraw(CFX_RenderDevice* pDevice,
659                                       CFX_Matrix* pUser2Device,
660#ifdef PDF_ENABLE_XFA
661                                       CPDF_RenderOptions* pOptions,
662                                       const FX_RECT& pClip) {
663#else
664                                       CPDF_RenderOptions* pOptions) {
665#endif  // PDF_ENABLE_XFA
666  m_curMatrix = *pUser2Device;
667  CPDFDoc_Environment* pEnv = m_pSDKDoc->GetEnv();
668
669#ifdef PDF_ENABLE_XFA
670  CPDFXFA_Page* pPage = GetPDFXFAPage();
671  if (!pPage)
672    return;
673
674  if (pPage->GetDocument()->GetDocType() == DOCTYPE_DYNAMIC_XFA) {
675    CFX_Graphics gs;
676    gs.Create(pDevice);
677    CFX_RectF rectClip;
678    rectClip.Set(static_cast<FX_FLOAT>(pClip.left),
679                 static_cast<FX_FLOAT>(pClip.top),
680                 static_cast<FX_FLOAT>(pClip.Width()),
681                 static_cast<FX_FLOAT>(pClip.Height()));
682    gs.SetClipRect(rectClip);
683    IXFA_RenderContext* pRenderContext = XFA_RenderContext_Create();
684    if (!pRenderContext)
685      return;
686    CXFA_RenderOptions renderOptions;
687    renderOptions.m_bHighlight = TRUE;
688    IXFA_PageView* xfaView = pPage->GetXFAPageView();
689    pRenderContext->StartRender(xfaView, &gs, *pUser2Device, renderOptions);
690    pRenderContext->DoRender();
691    pRenderContext->StopRender();
692    pRenderContext->Release();
693    IXFA_DocView* docView = xfaView->GetDocView();
694    if (!docView)
695      return;
696    CPDFSDK_Annot* annot = GetFocusAnnot();
697    if (!annot)
698      return;
699    // Render the focus widget
700    docView->GetWidgetHandler()->RenderWidget(annot->GetXFAWidget(), &gs,
701                                              pUser2Device, FALSE);
702    return;
703  }
704#endif  // PDF_ENABLE_XFA
705
706  // for pdf/static xfa.
707  CPDFSDK_AnnotIterator annotIterator(this, true);
708  while (CPDFSDK_Annot* pSDKAnnot = annotIterator.Next()) {
709    CPDFSDK_AnnotHandlerMgr* pAnnotHandlerMgr = pEnv->GetAnnotHandlerMgr();
710    pAnnotHandlerMgr->Annot_OnDraw(this, pSDKAnnot, pDevice, pUser2Device, 0);
711  }
712}
713
714const CPDF_Annot* CPDFSDK_PageView::GetPDFAnnotAtPoint(FX_FLOAT pageX,
715                                                       FX_FLOAT pageY) {
716  for (const CPDF_Annot* pAnnot : m_pAnnotList->All()) {
717    CFX_FloatRect annotRect;
718    pAnnot->GetRect(annotRect);
719    if (annotRect.Contains(pageX, pageY))
720      return pAnnot;
721  }
722  return nullptr;
723}
724
725const CPDF_Annot* CPDFSDK_PageView::GetPDFWidgetAtPoint(FX_FLOAT pageX,
726                                                        FX_FLOAT pageY) {
727  for (const CPDF_Annot* pAnnot : m_pAnnotList->All()) {
728    if (pAnnot->GetSubType() == "Widget") {
729      CFX_FloatRect annotRect;
730      pAnnot->GetRect(annotRect);
731      if (annotRect.Contains(pageX, pageY))
732        return pAnnot;
733    }
734  }
735  return nullptr;
736}
737
738CPDFSDK_Annot* CPDFSDK_PageView::GetFXAnnotAtPoint(FX_FLOAT pageX,
739                                                   FX_FLOAT pageY) {
740  CPDFDoc_Environment* pEnv = m_pSDKDoc->GetEnv();
741  CPDFSDK_AnnotHandlerMgr* pAnnotMgr = pEnv->GetAnnotHandlerMgr();
742  CPDFSDK_AnnotIterator annotIterator(this, false);
743  while (CPDFSDK_Annot* pSDKAnnot = annotIterator.Next()) {
744    CPDF_Rect rc = pAnnotMgr->Annot_OnGetViewBBox(this, pSDKAnnot);
745    if (rc.Contains(pageX, pageY))
746      return pSDKAnnot;
747  }
748
749  return nullptr;
750}
751
752CPDFSDK_Annot* CPDFSDK_PageView::GetFXWidgetAtPoint(FX_FLOAT pageX,
753                                                    FX_FLOAT pageY) {
754  CPDFDoc_Environment* pEnv = m_pSDKDoc->GetEnv();
755  CPDFSDK_AnnotHandlerMgr* pAnnotMgr = pEnv->GetAnnotHandlerMgr();
756  CPDFSDK_AnnotIterator annotIterator(this, false);
757  while (CPDFSDK_Annot* pSDKAnnot = annotIterator.Next()) {
758    bool bHitTest = pSDKAnnot->GetType() == "Widget";
759#ifdef PDF_ENABLE_XFA
760    bHitTest = bHitTest || pSDKAnnot->GetType() == FSDK_XFAWIDGET_TYPENAME;
761#endif  // PDF_ENABLE_XFA
762    if (bHitTest) {
763      pAnnotMgr->Annot_OnGetViewBBox(this, pSDKAnnot);
764      CPDF_Point point(pageX, pageY);
765      if (pAnnotMgr->Annot_OnHitTest(this, pSDKAnnot, point))
766        return pSDKAnnot;
767    }
768  }
769
770  return nullptr;
771}
772
773void CPDFSDK_PageView::KillFocusAnnotIfNeeded() {
774  // if there is a focused annot on the page, we should kill the focus first.
775  if (CPDFSDK_Annot* focusedAnnot = m_pSDKDoc->GetFocusAnnot()) {
776    if (pdfium::ContainsValue(m_fxAnnotArray, focusedAnnot))
777      KillFocusAnnot();
778  }
779}
780
781FX_BOOL CPDFSDK_PageView::Annot_HasAppearance(CPDF_Annot* pAnnot) {
782  CPDF_Dictionary* pAnnotDic = pAnnot->GetAnnotDict();
783  if (pAnnotDic)
784    return pAnnotDic->KeyExist("AS");
785  return FALSE;
786}
787
788CPDFSDK_Annot* CPDFSDK_PageView::AddAnnot(CPDF_Annot* pPDFAnnot) {
789  CPDFDoc_Environment* pEnv = m_pSDKDoc->GetEnv();
790  ASSERT(pEnv);
791  CPDFSDK_AnnotHandlerMgr* pAnnotHandler = pEnv->GetAnnotHandlerMgr();
792  CPDFSDK_Annot* pSDKAnnot = pAnnotHandler->NewAnnot(pPDFAnnot, this);
793  if (!pSDKAnnot)
794    return nullptr;
795
796  m_fxAnnotArray.push_back(pSDKAnnot);
797  pAnnotHandler->Annot_OnCreate(pSDKAnnot);
798  return pSDKAnnot;
799}
800
801#ifdef PDF_ENABLE_XFA
802CPDFSDK_Annot* CPDFSDK_PageView::AddAnnot(IXFA_Widget* pPDFAnnot) {
803  if (!pPDFAnnot)
804    return nullptr;
805
806  CPDFSDK_Annot* pSDKAnnot = GetAnnotByXFAWidget(pPDFAnnot);
807  if (pSDKAnnot)
808    return pSDKAnnot;
809
810  CPDFDoc_Environment* pEnv = m_pSDKDoc->GetEnv();
811  CPDFSDK_AnnotHandlerMgr* pAnnotHandler = pEnv->GetAnnotHandlerMgr();
812  pSDKAnnot = pAnnotHandler->NewAnnot(pPDFAnnot, this);
813  if (!pSDKAnnot)
814    return nullptr;
815
816  m_fxAnnotArray.push_back(pSDKAnnot);
817  return pSDKAnnot;
818}
819#endif  // PDF_ENABLE_XFA
820
821CPDFSDK_Annot* CPDFSDK_PageView::AddAnnot(CPDF_Dictionary* pDict) {
822  return pDict ? AddAnnot(pDict->GetString("Subtype"), pDict) : nullptr;
823}
824
825CPDFSDK_Annot* CPDFSDK_PageView::AddAnnot(const FX_CHAR* lpSubType,
826                                          CPDF_Dictionary* pDict) {
827  return NULL;
828}
829
830FX_BOOL CPDFSDK_PageView::DeleteAnnot(CPDFSDK_Annot* pAnnot) {
831#ifdef PDF_ENABLE_XFA
832  if (!pAnnot)
833    return FALSE;
834  CPDFXFA_Page* pPage = pAnnot->GetPDFXFAPage();
835  if (!pPage || (pPage->GetDocument()->GetDocType() != DOCTYPE_STATIC_XFA &&
836                 pPage->GetDocument()->GetDocType() != DOCTYPE_DYNAMIC_XFA))
837    return FALSE;
838
839  auto it = std::find(m_fxAnnotArray.begin(), m_fxAnnotArray.end(), pAnnot);
840  if (it != m_fxAnnotArray.end())
841    m_fxAnnotArray.erase(it);
842  if (m_CaptureWidget == pAnnot)
843    m_CaptureWidget = nullptr;
844
845  return TRUE;
846#else   // PDF_ENABLE_XFA
847  return FALSE;
848#endif  // PDF_ENABLE_XFA
849}
850
851CPDF_Document* CPDFSDK_PageView::GetPDFDocument() {
852  if (m_page) {
853#ifdef PDF_ENABLE_XFA
854    return m_page->GetDocument()->GetPDFDoc();
855#else   // PDF_ENABLE_XFA
856    return m_page->m_pDocument;
857#endif  // PDF_ENABLE_XFA
858  }
859  return NULL;
860}
861
862#ifdef PDF_ENABLE_XFA
863CPDF_Page* CPDFSDK_PageView::GetPDFPage() {
864  if (m_page) {
865    return m_page->GetPDFPage();
866  }
867  return NULL;
868}
869#endif  // PDF_ENABLE_XFA
870
871size_t CPDFSDK_PageView::CountAnnots() const {
872  return m_fxAnnotArray.size();
873}
874
875CPDFSDK_Annot* CPDFSDK_PageView::GetAnnot(size_t nIndex) {
876  return nIndex < m_fxAnnotArray.size() ? m_fxAnnotArray[nIndex] : nullptr;
877}
878
879CPDFSDK_Annot* CPDFSDK_PageView::GetAnnotByDict(CPDF_Dictionary* pDict) {
880  for (CPDFSDK_Annot* pAnnot : m_fxAnnotArray) {
881    if (pAnnot->GetPDFAnnot()->GetAnnotDict() == pDict)
882      return pAnnot;
883  }
884  return nullptr;
885}
886
887#ifdef PDF_ENABLE_XFA
888CPDFSDK_Annot* CPDFSDK_PageView::GetAnnotByXFAWidget(IXFA_Widget* hWidget) {
889  if (!hWidget)
890    return nullptr;
891
892  for (CPDFSDK_Annot* pAnnot : m_fxAnnotArray) {
893    if (pAnnot->GetXFAWidget() == hWidget)
894      return pAnnot;
895  }
896  return nullptr;
897}
898#endif  // PDF_ENABLE_XFA
899
900FX_BOOL CPDFSDK_PageView::OnLButtonDown(const CPDF_Point& point,
901                                        FX_UINT nFlag) {
902  CPDFDoc_Environment* pEnv = m_pSDKDoc->GetEnv();
903  ASSERT(pEnv);
904  CPDFSDK_Annot* pFXAnnot = GetFXWidgetAtPoint(point.x, point.y);
905  if (!pFXAnnot) {
906    KillFocusAnnot(nFlag);
907    return FALSE;
908  }
909
910  CPDFSDK_AnnotHandlerMgr* pAnnotHandlerMgr = pEnv->GetAnnotHandlerMgr();
911  FX_BOOL bRet =
912      pAnnotHandlerMgr->Annot_OnLButtonDown(this, pFXAnnot, nFlag, point);
913  if (bRet)
914    SetFocusAnnot(pFXAnnot);
915  return bRet;
916}
917
918#ifdef PDF_ENABLE_XFA
919FX_BOOL CPDFSDK_PageView::OnRButtonDown(const CPDF_Point& point,
920                                        FX_UINT nFlag) {
921  CPDFDoc_Environment* pEnv = m_pSDKDoc->GetEnv();
922  ASSERT(pEnv);
923  CPDFSDK_AnnotHandlerMgr* pAnnotHandlerMgr = pEnv->GetAnnotHandlerMgr();
924  ASSERT(pAnnotHandlerMgr);
925
926  CPDFSDK_Annot* pFXAnnot = GetFXWidgetAtPoint(point.x, point.y);
927
928  if (pFXAnnot == NULL)
929    return FALSE;
930
931  FX_BOOL bRet =
932      pAnnotHandlerMgr->Annot_OnRButtonDown(this, pFXAnnot, nFlag, point);
933  if (bRet) {
934    SetFocusAnnot(pFXAnnot);
935  }
936  return TRUE;
937}
938
939FX_BOOL CPDFSDK_PageView::OnRButtonUp(const CPDF_Point& point, FX_UINT nFlag) {
940  CPDFDoc_Environment* pEnv = m_pSDKDoc->GetEnv();
941  ASSERT(pEnv);
942  CPDFSDK_AnnotHandlerMgr* pAnnotHandlerMgr = pEnv->GetAnnotHandlerMgr();
943
944  CPDFSDK_Annot* pFXAnnot = GetFXWidgetAtPoint(point.x, point.y);
945
946  if (pFXAnnot == NULL)
947    return FALSE;
948
949  FX_BOOL bRet =
950      pAnnotHandlerMgr->Annot_OnRButtonUp(this, pFXAnnot, nFlag, point);
951  if (bRet) {
952    SetFocusAnnot(pFXAnnot);
953  }
954  return TRUE;
955}
956#endif  // PDF_ENABLE_XFA
957
958FX_BOOL CPDFSDK_PageView::OnLButtonUp(const CPDF_Point& point, FX_UINT nFlag) {
959  CPDFDoc_Environment* pEnv = m_pSDKDoc->GetEnv();
960  ASSERT(pEnv);
961  CPDFSDK_AnnotHandlerMgr* pAnnotHandlerMgr = pEnv->GetAnnotHandlerMgr();
962  CPDFSDK_Annot* pFXAnnot = GetFXWidgetAtPoint(point.x, point.y);
963  CPDFSDK_Annot* pFocusAnnot = GetFocusAnnot();
964  FX_BOOL bRet = FALSE;
965  if (pFocusAnnot && pFocusAnnot != pFXAnnot) {
966    // Last focus Annot gets a chance to handle the event.
967    bRet = pAnnotHandlerMgr->Annot_OnLButtonUp(this, pFocusAnnot, nFlag, point);
968  }
969  if (pFXAnnot && !bRet)
970    bRet = pAnnotHandlerMgr->Annot_OnLButtonUp(this, pFXAnnot, nFlag, point);
971  return bRet;
972}
973
974FX_BOOL CPDFSDK_PageView::OnMouseMove(const CPDF_Point& point, int nFlag) {
975  CPDFDoc_Environment* pEnv = m_pSDKDoc->GetEnv();
976  CPDFSDK_AnnotHandlerMgr* pAnnotHandlerMgr = pEnv->GetAnnotHandlerMgr();
977  if (CPDFSDK_Annot* pFXAnnot = GetFXWidgetAtPoint(point.x, point.y)) {
978    if (m_CaptureWidget && m_CaptureWidget != pFXAnnot) {
979      m_bExitWidget = TRUE;
980      m_bEnterWidget = FALSE;
981      pAnnotHandlerMgr->Annot_OnMouseExit(this, m_CaptureWidget, nFlag);
982    }
983    m_CaptureWidget = (CPDFSDK_Widget*)pFXAnnot;
984    m_bOnWidget = TRUE;
985    if (!m_bEnterWidget) {
986      m_bEnterWidget = TRUE;
987      m_bExitWidget = FALSE;
988      pAnnotHandlerMgr->Annot_OnMouseEnter(this, pFXAnnot, nFlag);
989    }
990    pAnnotHandlerMgr->Annot_OnMouseMove(this, pFXAnnot, nFlag, point);
991    return TRUE;
992  }
993  if (m_bOnWidget) {
994    m_bOnWidget = FALSE;
995    m_bExitWidget = TRUE;
996    m_bEnterWidget = FALSE;
997    if (m_CaptureWidget) {
998      pAnnotHandlerMgr->Annot_OnMouseExit(this, m_CaptureWidget, nFlag);
999      m_CaptureWidget = NULL;
1000    }
1001  }
1002  return FALSE;
1003}
1004
1005FX_BOOL CPDFSDK_PageView::OnMouseWheel(double deltaX,
1006                                       double deltaY,
1007                                       const CPDF_Point& point,
1008                                       int nFlag) {
1009  if (CPDFSDK_Annot* pAnnot = GetFXWidgetAtPoint(point.x, point.y)) {
1010    CPDFDoc_Environment* pEnv = m_pSDKDoc->GetEnv();
1011    CPDFSDK_AnnotHandlerMgr* pAnnotHandlerMgr = pEnv->GetAnnotHandlerMgr();
1012    return pAnnotHandlerMgr->Annot_OnMouseWheel(this, pAnnot, nFlag,
1013                                                (int)deltaY, point);
1014  }
1015  return FALSE;
1016}
1017
1018FX_BOOL CPDFSDK_PageView::OnChar(int nChar, FX_UINT nFlag) {
1019  if (CPDFSDK_Annot* pAnnot = GetFocusAnnot()) {
1020    CPDFDoc_Environment* pEnv = m_pSDKDoc->GetEnv();
1021    CPDFSDK_AnnotHandlerMgr* pAnnotHandlerMgr = pEnv->GetAnnotHandlerMgr();
1022    return pAnnotHandlerMgr->Annot_OnChar(pAnnot, nChar, nFlag);
1023  }
1024
1025  return FALSE;
1026}
1027
1028FX_BOOL CPDFSDK_PageView::OnKeyDown(int nKeyCode, int nFlag) {
1029  if (CPDFSDK_Annot* pAnnot = GetFocusAnnot()) {
1030    CPDFDoc_Environment* pEnv = m_pSDKDoc->GetEnv();
1031    CPDFSDK_AnnotHandlerMgr* pAnnotHandlerMgr = pEnv->GetAnnotHandlerMgr();
1032    return pAnnotHandlerMgr->Annot_OnKeyDown(pAnnot, nKeyCode, nFlag);
1033  }
1034  return FALSE;
1035}
1036
1037FX_BOOL CPDFSDK_PageView::OnKeyUp(int nKeyCode, int nFlag) {
1038  return FALSE;
1039}
1040
1041void CPDFSDK_PageView::LoadFXAnnots() {
1042  CPDFDoc_Environment* pEnv = m_pSDKDoc->GetEnv();
1043#ifdef PDF_ENABLE_XFA
1044  CPDFSDK_AnnotHandlerMgr* pAnnotHandlerMgr = pEnv->GetAnnotHandlerMgr();
1045#else
1046  FX_BOOL enableAPUpdate = CPDF_InterForm::UpdatingAPEnabled();
1047  // Disable the default AP construction.
1048  CPDF_InterForm::EnableUpdateAP(FALSE);
1049  m_pAnnotList.reset(new CPDF_AnnotList(m_page));
1050  CPDF_InterForm::EnableUpdateAP(enableAPUpdate);
1051  const size_t nCount = m_pAnnotList->Count();
1052#endif  // PDF_ENABLE_XFA
1053
1054  SetLock(TRUE);
1055
1056#ifdef PDF_ENABLE_XFA
1057  m_page->AddRef();
1058  if (m_pSDKDoc->GetXFADocument()->GetDocType() == DOCTYPE_DYNAMIC_XFA) {
1059    IXFA_PageView* pageView = NULL;
1060    pageView = m_page->GetXFAPageView();
1061    ASSERT(pageView != NULL);
1062
1063    IXFA_WidgetIterator* pWidgetHander = pageView->CreateWidgetIterator(
1064        XFA_TRAVERSEWAY_Form, XFA_WIDGETFILTER_Visible |
1065                                  XFA_WIDGETFILTER_Viewable |
1066                                  XFA_WIDGETFILTER_AllType);
1067    if (!pWidgetHander) {
1068      m_page->Release();
1069      SetLock(FALSE);
1070      return;
1071    }
1072
1073    while (IXFA_Widget* pXFAAnnot = pWidgetHander->MoveToNext()) {
1074      CPDFSDK_Annot* pAnnot = pAnnotHandlerMgr->NewAnnot(pXFAAnnot, this);
1075      if (!pAnnot)
1076        continue;
1077
1078      m_fxAnnotArray.push_back(pAnnot);
1079      pAnnotHandlerMgr->Annot_OnLoad(pAnnot);
1080    }
1081    pWidgetHander->Release();
1082  } else {
1083    CPDF_Page* pPage = m_page->GetPDFPage();
1084    ASSERT(pPage != NULL);
1085    FX_BOOL enableAPUpdate = CPDF_InterForm::UpdatingAPEnabled();
1086    // Disable the default AP construction.
1087    CPDF_InterForm::EnableUpdateAP(FALSE);
1088    m_pAnnotList.reset(new CPDF_AnnotList(pPage));
1089    CPDF_InterForm::EnableUpdateAP(enableAPUpdate);
1090
1091    const size_t nCount = m_pAnnotList->Count();
1092    for (size_t i = 0; i < nCount; ++i) {
1093      CPDF_Annot* pPDFAnnot = m_pAnnotList->GetAt(i);
1094      CheckUnSupportAnnot(GetPDFDocument(), pPDFAnnot);
1095
1096      CPDFSDK_Annot* pAnnot = pAnnotHandlerMgr->NewAnnot(pPDFAnnot, this);
1097      if (!pAnnot)
1098        continue;
1099      m_fxAnnotArray.push_back(pAnnot);
1100      pAnnotHandlerMgr->Annot_OnLoad(pAnnot);
1101    }
1102  }
1103  m_page->Release();
1104#else   // PDF_ENABLE_XFA
1105  for (size_t i = 0; i < nCount; ++i) {
1106    CPDF_Annot* pPDFAnnot = m_pAnnotList->GetAt(i);
1107    CPDF_Document* pDoc = GetPDFDocument();
1108    CheckUnSupportAnnot(pDoc, pPDFAnnot);
1109    CPDFSDK_AnnotHandlerMgr* pAnnotHandlerMgr = pEnv->GetAnnotHandlerMgr();
1110    CPDFSDK_Annot* pAnnot = pAnnotHandlerMgr->NewAnnot(pPDFAnnot, this);
1111    if (!pAnnot)
1112      continue;
1113    m_fxAnnotArray.push_back(pAnnot);
1114    pAnnotHandlerMgr->Annot_OnLoad(pAnnot);
1115  }
1116#endif  // PDF_ENABLE_XFA
1117
1118  SetLock(FALSE);
1119}
1120
1121void CPDFSDK_PageView::UpdateRects(CFX_RectArray& rects) {
1122  for (int i = 0; i < rects.GetSize(); i++) {
1123    CPDF_Rect rc = rects.GetAt(i);
1124    CPDFDoc_Environment* pEnv = m_pSDKDoc->GetEnv();
1125    pEnv->FFI_Invalidate(m_page, rc.left, rc.top, rc.right, rc.bottom);
1126  }
1127}
1128
1129void CPDFSDK_PageView::UpdateView(CPDFSDK_Annot* pAnnot) {
1130  CPDF_Rect rcWindow = pAnnot->GetRect();
1131  CPDFDoc_Environment* pEnv = m_pSDKDoc->GetEnv();
1132  pEnv->FFI_Invalidate(m_page, rcWindow.left, rcWindow.top, rcWindow.right,
1133                       rcWindow.bottom);
1134}
1135
1136int CPDFSDK_PageView::GetPageIndex() {
1137  if (m_page) {
1138#ifdef PDF_ENABLE_XFA
1139    CPDF_Dictionary* pDic = m_page->GetPDFPage()->m_pFormDict;
1140#else   // PDF_ENABLE_XFA
1141    CPDF_Dictionary* pDic = m_page->m_pFormDict;
1142#endif  // PDF_ENABLE_XFA
1143    CPDF_Document* pDoc = m_pSDKDoc->GetPDFDocument();
1144    if (pDoc && pDic) {
1145      return pDoc->GetPageIndex(pDic->GetObjNum());
1146    }
1147  }
1148  return -1;
1149}
1150
1151bool CPDFSDK_PageView::IsValidAnnot(const CPDF_Annot* p) const {
1152  if (!p)
1153    return false;
1154
1155  const auto& annots = m_pAnnotList->All();
1156  return pdfium::ContainsValue(annots, p);
1157}
1158
1159CPDFSDK_Annot* CPDFSDK_PageView::GetFocusAnnot() {
1160  CPDFSDK_Annot* pFocusAnnot = m_pSDKDoc->GetFocusAnnot();
1161  if (!pFocusAnnot)
1162    return nullptr;
1163
1164  for (CPDFSDK_Annot* pAnnot : m_fxAnnotArray) {
1165    if (pAnnot == pFocusAnnot)
1166      return pAnnot;
1167  }
1168  return nullptr;
1169}
1170