| OLD | NEW |
| (Empty) |
| 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 "fpdfsdk/include/fsdk_mgr.h" | |
| 8 | |
| 9 #include <algorithm> | |
| 10 #include <memory> | |
| 11 | |
| 12 #include "core/fpdfapi/fpdf_page/include/cpdf_page.h" | |
| 13 #include "core/fpdfapi/fpdf_parser/include/cpdf_array.h" | |
| 14 #include "core/fpdfapi/fpdf_parser/include/cpdf_document.h" | |
| 15 #include "core/fpdfapi/fpdf_render/include/cpdf_renderoptions.h" | |
| 16 #include "core/fpdfdoc/include/cpdf_docjsactions.h" | |
| 17 #include "core/fpdfdoc/include/cpdf_interform.h" | |
| 18 #include "core/fxcrt/include/cfx_retain_ptr.h" | |
| 19 #include "core/fxge/include/cfx_renderdevice.h" | |
| 20 #include "fpdfsdk/formfiller/cffl_formfiller.h" | |
| 21 #include "fpdfsdk/include/cpdfsdk_annothandlermgr.h" | |
| 22 #include "fpdfsdk/include/cpdfsdk_annotiterator.h" | |
| 23 #include "fpdfsdk/include/cpdfsdk_interform.h" | |
| 24 #include "fpdfsdk/include/cpdfsdk_widget.h" | |
| 25 #include "fpdfsdk/include/fsdk_define.h" | |
| 26 #include "fpdfsdk/include/ipdfsdk_annothandler.h" | |
| 27 #include "fpdfsdk/javascript/ijs_runtime.h" | |
| 28 #include "public/fpdf_ext.h" | |
| 29 #include "third_party/base/stl_util.h" | |
| 30 | |
| 31 #ifdef PDF_ENABLE_XFA | |
| 32 #include "fpdfsdk/fpdfxfa/include/fpdfxfa_app.h" | |
| 33 #include "fpdfsdk/fpdfxfa/include/fpdfxfa_doc.h" | |
| 34 #include "fpdfsdk/fpdfxfa/include/fpdfxfa_page.h" | |
| 35 #include "fpdfsdk/fpdfxfa/include/fpdfxfa_util.h" | |
| 36 #include "xfa/fxfa/include/xfa_ffdocview.h" | |
| 37 #include "xfa/fxfa/include/xfa_ffpageview.h" | |
| 38 #include "xfa/fxfa/include/xfa_ffwidgethandler.h" | |
| 39 #include "xfa/fxfa/include/xfa_rendercontext.h" | |
| 40 #include "xfa/fxgraphics/include/cfx_graphics.h" | |
| 41 #endif // PDF_ENABLE_XFA | |
| 42 | |
| 43 #if _FX_OS_ == _FX_ANDROID_ | |
| 44 #include "time.h" | |
| 45 #else | |
| 46 #include <ctime> | |
| 47 #endif | |
| 48 | |
| 49 namespace { | |
| 50 | |
| 51 // NOTE: |bsUTF16LE| must outlive the use of the result. Care must be taken | |
| 52 // since modifying the result would impact |bsUTF16LE|. | |
| 53 FPDF_WIDESTRING AsFPDFWideString(CFX_ByteString* bsUTF16LE) { | |
| 54 return reinterpret_cast<FPDF_WIDESTRING>( | |
| 55 bsUTF16LE->GetBuffer(bsUTF16LE->GetLength())); | |
| 56 } | |
| 57 | |
| 58 } // namespace | |
| 59 | |
| 60 CPDFDoc_Environment::CPDFDoc_Environment(UnderlyingDocumentType* pDoc, | |
| 61 FPDF_FORMFILLINFO* pFFinfo) | |
| 62 : m_pInfo(pFFinfo), m_pSDKDoc(nullptr), m_pUnderlyingDoc(pDoc) { | |
| 63 m_pSysHandler.reset(new CFX_SystemHandler(this)); | |
| 64 } | |
| 65 | |
| 66 CPDFDoc_Environment::~CPDFDoc_Environment() { | |
| 67 #ifdef PDF_ENABLE_XFA | |
| 68 CPDFXFA_App* pProvider = CPDFXFA_App::GetInstance(); | |
| 69 if (pProvider->m_pEnvList.GetSize() == 0) | |
| 70 pProvider->SetJavaScriptInitialized(FALSE); | |
| 71 #endif // PDF_ENABLE_XFA | |
| 72 if (m_pInfo && m_pInfo->Release) | |
| 73 m_pInfo->Release(m_pInfo); | |
| 74 } | |
| 75 | |
| 76 int CPDFDoc_Environment::JS_appAlert(const FX_WCHAR* Msg, | |
| 77 const FX_WCHAR* Title, | |
| 78 FX_UINT Type, | |
| 79 FX_UINT Icon) { | |
| 80 if (!m_pInfo || !m_pInfo->m_pJsPlatform || | |
| 81 !m_pInfo->m_pJsPlatform->app_alert) { | |
| 82 return -1; | |
| 83 } | |
| 84 CFX_ByteString bsMsg = CFX_WideString(Msg).UTF16LE_Encode(); | |
| 85 CFX_ByteString bsTitle = CFX_WideString(Title).UTF16LE_Encode(); | |
| 86 return m_pInfo->m_pJsPlatform->app_alert( | |
| 87 m_pInfo->m_pJsPlatform, AsFPDFWideString(&bsMsg), | |
| 88 AsFPDFWideString(&bsTitle), Type, Icon); | |
| 89 } | |
| 90 | |
| 91 int CPDFDoc_Environment::JS_appResponse(const FX_WCHAR* Question, | |
| 92 const FX_WCHAR* Title, | |
| 93 const FX_WCHAR* Default, | |
| 94 const FX_WCHAR* cLabel, | |
| 95 FPDF_BOOL bPassword, | |
| 96 void* response, | |
| 97 int length) { | |
| 98 if (!m_pInfo || !m_pInfo->m_pJsPlatform || | |
| 99 !m_pInfo->m_pJsPlatform->app_response) { | |
| 100 return -1; | |
| 101 } | |
| 102 CFX_ByteString bsQuestion = CFX_WideString(Question).UTF16LE_Encode(); | |
| 103 CFX_ByteString bsTitle = CFX_WideString(Title).UTF16LE_Encode(); | |
| 104 CFX_ByteString bsDefault = CFX_WideString(Default).UTF16LE_Encode(); | |
| 105 CFX_ByteString bsLabel = CFX_WideString(cLabel).UTF16LE_Encode(); | |
| 106 return m_pInfo->m_pJsPlatform->app_response( | |
| 107 m_pInfo->m_pJsPlatform, AsFPDFWideString(&bsQuestion), | |
| 108 AsFPDFWideString(&bsTitle), AsFPDFWideString(&bsDefault), | |
| 109 AsFPDFWideString(&bsLabel), bPassword, response, length); | |
| 110 } | |
| 111 | |
| 112 void CPDFDoc_Environment::JS_appBeep(int nType) { | |
| 113 if (!m_pInfo || !m_pInfo->m_pJsPlatform || | |
| 114 !m_pInfo->m_pJsPlatform->app_beep) { | |
| 115 return; | |
| 116 } | |
| 117 m_pInfo->m_pJsPlatform->app_beep(m_pInfo->m_pJsPlatform, nType); | |
| 118 } | |
| 119 | |
| 120 CFX_WideString CPDFDoc_Environment::JS_fieldBrowse() { | |
| 121 if (!m_pInfo || !m_pInfo->m_pJsPlatform || | |
| 122 !m_pInfo->m_pJsPlatform->Field_browse) { | |
| 123 return CFX_WideString(); | |
| 124 } | |
| 125 const int nRequiredLen = | |
| 126 m_pInfo->m_pJsPlatform->Field_browse(m_pInfo->m_pJsPlatform, nullptr, 0); | |
| 127 if (nRequiredLen <= 0) | |
| 128 return CFX_WideString(); | |
| 129 | |
| 130 std::unique_ptr<char[]> pBuff(new char[nRequiredLen]); | |
| 131 memset(pBuff.get(), 0, nRequiredLen); | |
| 132 const int nActualLen = m_pInfo->m_pJsPlatform->Field_browse( | |
| 133 m_pInfo->m_pJsPlatform, pBuff.get(), nRequiredLen); | |
| 134 if (nActualLen <= 0 || nActualLen > nRequiredLen) | |
| 135 return CFX_WideString(); | |
| 136 | |
| 137 return CFX_WideString::FromLocal(CFX_ByteStringC(pBuff.get(), nActualLen)); | |
| 138 } | |
| 139 | |
| 140 CFX_WideString CPDFDoc_Environment::JS_docGetFilePath() { | |
| 141 if (!m_pInfo || !m_pInfo->m_pJsPlatform || | |
| 142 !m_pInfo->m_pJsPlatform->Doc_getFilePath) { | |
| 143 return CFX_WideString(); | |
| 144 } | |
| 145 const int nRequiredLen = m_pInfo->m_pJsPlatform->Doc_getFilePath( | |
| 146 m_pInfo->m_pJsPlatform, nullptr, 0); | |
| 147 if (nRequiredLen <= 0) | |
| 148 return CFX_WideString(); | |
| 149 | |
| 150 std::unique_ptr<char[]> pBuff(new char[nRequiredLen]); | |
| 151 memset(pBuff.get(), 0, nRequiredLen); | |
| 152 const int nActualLen = m_pInfo->m_pJsPlatform->Doc_getFilePath( | |
| 153 m_pInfo->m_pJsPlatform, pBuff.get(), nRequiredLen); | |
| 154 if (nActualLen <= 0 || nActualLen > nRequiredLen) | |
| 155 return CFX_WideString(); | |
| 156 | |
| 157 return CFX_WideString::FromLocal(CFX_ByteStringC(pBuff.get(), nActualLen)); | |
| 158 } | |
| 159 | |
| 160 void CPDFDoc_Environment::JS_docSubmitForm(void* formData, | |
| 161 int length, | |
| 162 const FX_WCHAR* URL) { | |
| 163 if (!m_pInfo || !m_pInfo->m_pJsPlatform || | |
| 164 !m_pInfo->m_pJsPlatform->Doc_submitForm) { | |
| 165 return; | |
| 166 } | |
| 167 CFX_ByteString bsDestination = CFX_WideString(URL).UTF16LE_Encode(); | |
| 168 m_pInfo->m_pJsPlatform->Doc_submitForm(m_pInfo->m_pJsPlatform, formData, | |
| 169 length, | |
| 170 AsFPDFWideString(&bsDestination)); | |
| 171 } | |
| 172 | |
| 173 void CPDFDoc_Environment::JS_docmailForm(void* mailData, | |
| 174 int length, | |
| 175 FPDF_BOOL bUI, | |
| 176 const FX_WCHAR* To, | |
| 177 const FX_WCHAR* Subject, | |
| 178 const FX_WCHAR* CC, | |
| 179 const FX_WCHAR* BCC, | |
| 180 const FX_WCHAR* Msg) { | |
| 181 if (!m_pInfo || !m_pInfo->m_pJsPlatform || | |
| 182 !m_pInfo->m_pJsPlatform->Doc_mail) { | |
| 183 return; | |
| 184 } | |
| 185 CFX_ByteString bsTo = CFX_WideString(To).UTF16LE_Encode(); | |
| 186 CFX_ByteString bsSubject = CFX_WideString(Subject).UTF16LE_Encode(); | |
| 187 CFX_ByteString bsCC = CFX_WideString(CC).UTF16LE_Encode(); | |
| 188 CFX_ByteString bsBcc = CFX_WideString(BCC).UTF16LE_Encode(); | |
| 189 CFX_ByteString bsMsg = CFX_WideString(Msg).UTF16LE_Encode(); | |
| 190 m_pInfo->m_pJsPlatform->Doc_mail( | |
| 191 m_pInfo->m_pJsPlatform, mailData, length, bUI, AsFPDFWideString(&bsTo), | |
| 192 AsFPDFWideString(&bsSubject), AsFPDFWideString(&bsCC), | |
| 193 AsFPDFWideString(&bsBcc), AsFPDFWideString(&bsMsg)); | |
| 194 } | |
| 195 | |
| 196 void CPDFDoc_Environment::JS_docprint(FPDF_BOOL bUI, | |
| 197 int nStart, | |
| 198 int nEnd, | |
| 199 FPDF_BOOL bSilent, | |
| 200 FPDF_BOOL bShrinkToFit, | |
| 201 FPDF_BOOL bPrintAsImage, | |
| 202 FPDF_BOOL bReverse, | |
| 203 FPDF_BOOL bAnnotations) { | |
| 204 if (!m_pInfo || !m_pInfo->m_pJsPlatform || | |
| 205 !m_pInfo->m_pJsPlatform->Doc_print) { | |
| 206 return; | |
| 207 } | |
| 208 m_pInfo->m_pJsPlatform->Doc_print(m_pInfo->m_pJsPlatform, bUI, nStart, nEnd, | |
| 209 bSilent, bShrinkToFit, bPrintAsImage, | |
| 210 bReverse, bAnnotations); | |
| 211 } | |
| 212 | |
| 213 void CPDFDoc_Environment::JS_docgotoPage(int nPageNum) { | |
| 214 if (!m_pInfo || !m_pInfo->m_pJsPlatform || | |
| 215 !m_pInfo->m_pJsPlatform->Doc_gotoPage) { | |
| 216 return; | |
| 217 } | |
| 218 m_pInfo->m_pJsPlatform->Doc_gotoPage(m_pInfo->m_pJsPlatform, nPageNum); | |
| 219 } | |
| 220 | |
| 221 IJS_Runtime* CPDFDoc_Environment::GetJSRuntime() { | |
| 222 if (!IsJSInitiated()) | |
| 223 return nullptr; | |
| 224 if (!m_pJSRuntime) | |
| 225 m_pJSRuntime.reset(IJS_Runtime::Create(this)); | |
| 226 return m_pJSRuntime.get(); | |
| 227 } | |
| 228 | |
| 229 CPDFSDK_AnnotHandlerMgr* CPDFDoc_Environment::GetAnnotHandlerMgr() { | |
| 230 if (!m_pAnnotHandlerMgr) | |
| 231 m_pAnnotHandlerMgr.reset(new CPDFSDK_AnnotHandlerMgr(this)); | |
| 232 return m_pAnnotHandlerMgr.get(); | |
| 233 } | |
| 234 | |
| 235 CPDFSDK_ActionHandler* CPDFDoc_Environment::GetActionHander() { | |
| 236 if (!m_pActionHandler) | |
| 237 m_pActionHandler.reset(new CPDFSDK_ActionHandler()); | |
| 238 return m_pActionHandler.get(); | |
| 239 } | |
| 240 | |
| 241 CFFL_IFormFiller* CPDFDoc_Environment::GetIFormFiller() { | |
| 242 if (!m_pIFormFiller) | |
| 243 m_pIFormFiller.reset(new CFFL_IFormFiller(this)); | |
| 244 return m_pIFormFiller.get(); | |
| 245 } | |
| 246 | |
| 247 // static | |
| 248 CPDFSDK_Document* CPDFSDK_Document::FromFPDFFormHandle( | |
| 249 FPDF_FORMHANDLE hHandle) { | |
| 250 CPDFDoc_Environment* pEnv = static_cast<CPDFDoc_Environment*>(hHandle); | |
| 251 return pEnv ? pEnv->GetSDKDocument() : nullptr; | |
| 252 } | |
| 253 | |
| 254 CPDFSDK_Document::CPDFSDK_Document(UnderlyingDocumentType* pDoc, | |
| 255 CPDFDoc_Environment* pEnv) | |
| 256 : m_pDoc(pDoc), | |
| 257 m_pFocusAnnot(nullptr), | |
| 258 m_pEnv(pEnv), | |
| 259 m_bChangeMask(FALSE), | |
| 260 m_bBeingDestroyed(FALSE) {} | |
| 261 | |
| 262 CPDFSDK_Document::~CPDFSDK_Document() { | |
| 263 m_bBeingDestroyed = TRUE; | |
| 264 | |
| 265 for (auto& it : m_pageMap) | |
| 266 it.second->KillFocusAnnotIfNeeded(); | |
| 267 | |
| 268 for (auto& it : m_pageMap) | |
| 269 delete it.second; | |
| 270 m_pageMap.clear(); | |
| 271 } | |
| 272 | |
| 273 CPDFSDK_PageView* CPDFSDK_Document::GetPageView( | |
| 274 UnderlyingPageType* pUnderlyingPage, | |
| 275 bool ReNew) { | |
| 276 auto it = m_pageMap.find(pUnderlyingPage); | |
| 277 if (it != m_pageMap.end()) | |
| 278 return it->second; | |
| 279 | |
| 280 if (!ReNew) | |
| 281 return nullptr; | |
| 282 | |
| 283 CPDFSDK_PageView* pPageView = new CPDFSDK_PageView(this, pUnderlyingPage); | |
| 284 m_pageMap[pUnderlyingPage] = pPageView; | |
| 285 // Delay to load all the annotations, to avoid endless loop. | |
| 286 pPageView->LoadFXAnnots(); | |
| 287 return pPageView; | |
| 288 } | |
| 289 | |
| 290 CPDFSDK_PageView* CPDFSDK_Document::GetCurrentView() { | |
| 291 UnderlyingPageType* pPage = | |
| 292 UnderlyingFromFPDFPage(m_pEnv->FFI_GetCurrentPage(m_pDoc)); | |
| 293 return pPage ? GetPageView(pPage, true) : nullptr; | |
| 294 } | |
| 295 | |
| 296 CPDFSDK_PageView* CPDFSDK_Document::GetPageView(int nIndex) { | |
| 297 UnderlyingPageType* pTempPage = | |
| 298 UnderlyingFromFPDFPage(m_pEnv->FFI_GetPage(m_pDoc, nIndex)); | |
| 299 if (!pTempPage) | |
| 300 return nullptr; | |
| 301 | |
| 302 auto it = m_pageMap.find(pTempPage); | |
| 303 return it != m_pageMap.end() ? it->second : nullptr; | |
| 304 } | |
| 305 | |
| 306 void CPDFSDK_Document::ProcJavascriptFun() { | |
| 307 CPDF_Document* pPDFDoc = GetPDFDocument(); | |
| 308 CPDF_DocJSActions docJS(pPDFDoc); | |
| 309 int iCount = docJS.CountJSActions(); | |
| 310 if (iCount < 1) | |
| 311 return; | |
| 312 for (int i = 0; i < iCount; i++) { | |
| 313 CFX_ByteString csJSName; | |
| 314 CPDF_Action jsAction = docJS.GetJSAction(i, csJSName); | |
| 315 if (m_pEnv->GetActionHander()) | |
| 316 m_pEnv->GetActionHander()->DoAction_JavaScript( | |
| 317 jsAction, CFX_WideString::FromLocal(csJSName.AsStringC()), this); | |
| 318 } | |
| 319 } | |
| 320 | |
| 321 FX_BOOL CPDFSDK_Document::ProcOpenAction() { | |
| 322 if (!m_pDoc) | |
| 323 return FALSE; | |
| 324 | |
| 325 CPDF_Dictionary* pRoot = GetPDFDocument()->GetRoot(); | |
| 326 if (!pRoot) | |
| 327 return FALSE; | |
| 328 | |
| 329 CPDF_Object* pOpenAction = pRoot->GetDictBy("OpenAction"); | |
| 330 if (!pOpenAction) | |
| 331 pOpenAction = pRoot->GetArrayBy("OpenAction"); | |
| 332 | |
| 333 if (!pOpenAction) | |
| 334 return FALSE; | |
| 335 | |
| 336 if (pOpenAction->IsArray()) | |
| 337 return TRUE; | |
| 338 | |
| 339 if (CPDF_Dictionary* pDict = pOpenAction->AsDictionary()) { | |
| 340 CPDF_Action action(pDict); | |
| 341 if (m_pEnv->GetActionHander()) | |
| 342 m_pEnv->GetActionHander()->DoAction_DocOpen(action, this); | |
| 343 return TRUE; | |
| 344 } | |
| 345 return FALSE; | |
| 346 } | |
| 347 | |
| 348 CPDF_OCContext* CPDFSDK_Document::GetOCContext() { | |
| 349 if (!m_pOccontent) { | |
| 350 m_pOccontent.reset( | |
| 351 new CPDF_OCContext(GetPDFDocument(), CPDF_OCContext::View)); | |
| 352 } | |
| 353 return m_pOccontent.get(); | |
| 354 } | |
| 355 | |
| 356 void CPDFSDK_Document::RemovePageView(UnderlyingPageType* pUnderlyingPage) { | |
| 357 auto it = m_pageMap.find(pUnderlyingPage); | |
| 358 if (it == m_pageMap.end()) | |
| 359 return; | |
| 360 | |
| 361 CPDFSDK_PageView* pPageView = it->second; | |
| 362 if (pPageView->IsLocked()) | |
| 363 return; | |
| 364 | |
| 365 // This must happen before we remove |pPageView| from the map because | |
| 366 // |KillFocusAnnotIfNeeded| can call into the |GetPage| method which will | |
| 367 // look for this page view in the map, if it doesn't find it a new one will | |
| 368 // be created. We then have two page views pointing to the same page and | |
| 369 // bad things happen. | |
| 370 pPageView->KillFocusAnnotIfNeeded(); | |
| 371 | |
| 372 // Remove the page from the map to make sure we don't accidentally attempt | |
| 373 // to use the |pPageView| while we're cleaning it up. | |
| 374 m_pageMap.erase(it); | |
| 375 | |
| 376 delete pPageView; | |
| 377 } | |
| 378 | |
| 379 UnderlyingPageType* CPDFSDK_Document::GetPage(int nIndex) { | |
| 380 return UnderlyingFromFPDFPage(m_pEnv->FFI_GetPage(m_pDoc, nIndex)); | |
| 381 } | |
| 382 | |
| 383 CPDFSDK_InterForm* CPDFSDK_Document::GetInterForm() { | |
| 384 if (!m_pInterForm) | |
| 385 m_pInterForm.reset(new CPDFSDK_InterForm(this)); | |
| 386 return m_pInterForm.get(); | |
| 387 } | |
| 388 | |
| 389 void CPDFSDK_Document::UpdateAllViews(CPDFSDK_PageView* pSender, | |
| 390 CPDFSDK_Annot* pAnnot) { | |
| 391 for (const auto& it : m_pageMap) { | |
| 392 CPDFSDK_PageView* pPageView = it.second; | |
| 393 if (pPageView != pSender) { | |
| 394 pPageView->UpdateView(pAnnot); | |
| 395 } | |
| 396 } | |
| 397 } | |
| 398 | |
| 399 CPDFSDK_Annot* CPDFSDK_Document::GetFocusAnnot() { | |
| 400 return m_pFocusAnnot; | |
| 401 } | |
| 402 | |
| 403 FX_BOOL CPDFSDK_Document::SetFocusAnnot(CPDFSDK_Annot* pAnnot, FX_UINT nFlag) { | |
| 404 if (m_bBeingDestroyed) | |
| 405 return FALSE; | |
| 406 | |
| 407 if (m_pFocusAnnot == pAnnot) | |
| 408 return TRUE; | |
| 409 | |
| 410 if (m_pFocusAnnot) { | |
| 411 if (!KillFocusAnnot(nFlag)) | |
| 412 return FALSE; | |
| 413 } | |
| 414 | |
| 415 if (!pAnnot) | |
| 416 return FALSE; | |
| 417 | |
| 418 #ifdef PDF_ENABLE_XFA | |
| 419 CPDFSDK_Annot* pLastFocusAnnot = m_pFocusAnnot; | |
| 420 #endif // PDF_ENABLE_XFA | |
| 421 CPDFSDK_PageView* pPageView = pAnnot->GetPageView(); | |
| 422 if (pPageView && pPageView->IsValid()) { | |
| 423 CPDFSDK_AnnotHandlerMgr* pAnnotHandler = m_pEnv->GetAnnotHandlerMgr(); | |
| 424 if (!m_pFocusAnnot) { | |
| 425 #ifdef PDF_ENABLE_XFA | |
| 426 if (!pAnnotHandler->Annot_OnChangeFocus(pAnnot, pLastFocusAnnot)) | |
| 427 return FALSE; | |
| 428 #endif // PDF_ENABLE_XFA | |
| 429 if (!pAnnotHandler->Annot_OnSetFocus(pAnnot, nFlag)) | |
| 430 return FALSE; | |
| 431 if (!m_pFocusAnnot) { | |
| 432 m_pFocusAnnot = pAnnot; | |
| 433 return TRUE; | |
| 434 } | |
| 435 } | |
| 436 } | |
| 437 return FALSE; | |
| 438 } | |
| 439 | |
| 440 FX_BOOL CPDFSDK_Document::KillFocusAnnot(FX_UINT nFlag) { | |
| 441 if (m_pFocusAnnot) { | |
| 442 CPDFSDK_AnnotHandlerMgr* pAnnotHandler = m_pEnv->GetAnnotHandlerMgr(); | |
| 443 CPDFSDK_Annot* pFocusAnnot = m_pFocusAnnot; | |
| 444 m_pFocusAnnot = nullptr; | |
| 445 | |
| 446 #ifdef PDF_ENABLE_XFA | |
| 447 if (!pAnnotHandler->Annot_OnChangeFocus(nullptr, pFocusAnnot)) | |
| 448 return FALSE; | |
| 449 #endif // PDF_ENABLE_XFA | |
| 450 | |
| 451 if (pAnnotHandler->Annot_OnKillFocus(pFocusAnnot, nFlag)) { | |
| 452 if (pFocusAnnot->GetAnnotSubtype() == CPDF_Annot::Subtype::WIDGET) { | |
| 453 CPDFSDK_Widget* pWidget = (CPDFSDK_Widget*)pFocusAnnot; | |
| 454 int nFieldType = pWidget->GetFieldType(); | |
| 455 if (FIELDTYPE_TEXTFIELD == nFieldType || | |
| 456 FIELDTYPE_COMBOBOX == nFieldType) { | |
| 457 m_pEnv->FFI_OnSetFieldInputFocus(nullptr, nullptr, 0, FALSE); | |
| 458 } | |
| 459 } | |
| 460 | |
| 461 if (!m_pFocusAnnot) | |
| 462 return TRUE; | |
| 463 } else { | |
| 464 m_pFocusAnnot = pFocusAnnot; | |
| 465 } | |
| 466 } | |
| 467 return FALSE; | |
| 468 } | |
| 469 | |
| 470 void CPDFSDK_Document::OnCloseDocument() { | |
| 471 KillFocusAnnot(); | |
| 472 } | |
| 473 | |
| 474 FX_BOOL CPDFSDK_Document::GetPermissions(int nFlag) { | |
| 475 return GetPDFDocument()->GetUserPermissions() & nFlag; | |
| 476 } | |
| 477 | |
| 478 IJS_Runtime* CPDFSDK_Document::GetJsRuntime() { | |
| 479 return m_pEnv->GetJSRuntime(); | |
| 480 } | |
| 481 | |
| 482 CFX_WideString CPDFSDK_Document::GetPath() { | |
| 483 return m_pEnv->JS_docGetFilePath(); | |
| 484 } | |
| 485 | |
| 486 CPDFSDK_PageView::CPDFSDK_PageView(CPDFSDK_Document* pSDKDoc, | |
| 487 UnderlyingPageType* page) | |
| 488 : m_page(page), | |
| 489 m_pSDKDoc(pSDKDoc), | |
| 490 m_CaptureWidget(nullptr), | |
| 491 #ifndef PDF_ENABLE_XFA | |
| 492 m_bOwnsPage(false), | |
| 493 #endif // PDF_ENABLE_XFA | |
| 494 m_bEnterWidget(FALSE), | |
| 495 m_bExitWidget(FALSE), | |
| 496 m_bOnWidget(FALSE), | |
| 497 m_bValid(FALSE), | |
| 498 m_bLocked(FALSE) { | |
| 499 CPDFSDK_InterForm* pInterForm = pSDKDoc->GetInterForm(); | |
| 500 if (pInterForm) { | |
| 501 CPDF_InterForm* pPDFInterForm = pInterForm->GetInterForm(); | |
| 502 #ifdef PDF_ENABLE_XFA | |
| 503 if (page->GetPDFPage()) | |
| 504 pPDFInterForm->FixPageFields(page->GetPDFPage()); | |
| 505 #else // PDF_ENABLE_XFA | |
| 506 pPDFInterForm->FixPageFields(page); | |
| 507 #endif // PDF_ENABLE_XFA | |
| 508 } | |
| 509 #ifndef PDF_ENABLE_XFA | |
| 510 m_page->SetView(this); | |
| 511 #endif // PDF_ENABLE_XFA | |
| 512 } | |
| 513 | |
| 514 CPDFSDK_PageView::~CPDFSDK_PageView() { | |
| 515 #ifndef PDF_ENABLE_XFA | |
| 516 // The call to |ReleaseAnnot| can cause the page pointed to by |m_page| to | |
| 517 // be freed, which will cause issues if we try to cleanup the pageview pointer | |
| 518 // in |m_page|. So, reset the pageview pointer before doing anything else. | |
| 519 m_page->SetView(nullptr); | |
| 520 #endif // PDF_ENABLE_XFA | |
| 521 | |
| 522 CPDFDoc_Environment* pEnv = m_pSDKDoc->GetEnv(); | |
| 523 CPDFSDK_AnnotHandlerMgr* pAnnotHandlerMgr = pEnv->GetAnnotHandlerMgr(); | |
| 524 for (CPDFSDK_Annot* pAnnot : m_fxAnnotArray) | |
| 525 pAnnotHandlerMgr->ReleaseAnnot(pAnnot); | |
| 526 | |
| 527 m_fxAnnotArray.clear(); | |
| 528 m_pAnnotList.reset(); | |
| 529 | |
| 530 #ifndef PDF_ENABLE_XFA | |
| 531 if (m_bOwnsPage) | |
| 532 delete m_page; | |
| 533 #endif // PDF_ENABLE_XFA | |
| 534 } | |
| 535 | |
| 536 void CPDFSDK_PageView::PageView_OnDraw(CFX_RenderDevice* pDevice, | |
| 537 CFX_Matrix* pUser2Device, | |
| 538 #ifdef PDF_ENABLE_XFA | |
| 539 CPDF_RenderOptions* pOptions, | |
| 540 const FX_RECT& pClip) { | |
| 541 #else | |
| 542 CPDF_RenderOptions* pOptions) { | |
| 543 #endif // PDF_ENABLE_XFA | |
| 544 m_curMatrix = *pUser2Device; | |
| 545 CPDFDoc_Environment* pEnv = m_pSDKDoc->GetEnv(); | |
| 546 | |
| 547 #ifdef PDF_ENABLE_XFA | |
| 548 CPDFXFA_Page* pPage = GetPDFXFAPage(); | |
| 549 if (!pPage) | |
| 550 return; | |
| 551 | |
| 552 if (pPage->GetDocument()->GetDocType() == DOCTYPE_DYNAMIC_XFA) { | |
| 553 CFX_Graphics gs; | |
| 554 gs.Create(pDevice); | |
| 555 CFX_RectF rectClip; | |
| 556 rectClip.Set(static_cast<FX_FLOAT>(pClip.left), | |
| 557 static_cast<FX_FLOAT>(pClip.top), | |
| 558 static_cast<FX_FLOAT>(pClip.Width()), | |
| 559 static_cast<FX_FLOAT>(pClip.Height())); | |
| 560 gs.SetClipRect(rectClip); | |
| 561 std::unique_ptr<CXFA_RenderContext> pRenderContext(new CXFA_RenderContext); | |
| 562 CXFA_RenderOptions renderOptions; | |
| 563 renderOptions.m_bHighlight = TRUE; | |
| 564 CXFA_FFPageView* xfaView = pPage->GetXFAPageView(); | |
| 565 pRenderContext->StartRender(xfaView, &gs, *pUser2Device, renderOptions); | |
| 566 pRenderContext->DoRender(); | |
| 567 pRenderContext->StopRender(); | |
| 568 CXFA_FFDocView* docView = xfaView->GetDocView(); | |
| 569 if (!docView) | |
| 570 return; | |
| 571 CPDFSDK_Annot* annot = GetFocusAnnot(); | |
| 572 if (!annot) | |
| 573 return; | |
| 574 // Render the focus widget | |
| 575 docView->GetWidgetHandler()->RenderWidget(annot->GetXFAWidget(), &gs, | |
| 576 pUser2Device, FALSE); | |
| 577 return; | |
| 578 } | |
| 579 #endif // PDF_ENABLE_XFA | |
| 580 | |
| 581 // for pdf/static xfa. | |
| 582 CPDFSDK_AnnotIterator annotIterator(this, true); | |
| 583 while (CPDFSDK_Annot* pSDKAnnot = annotIterator.Next()) { | |
| 584 CPDFSDK_AnnotHandlerMgr* pAnnotHandlerMgr = pEnv->GetAnnotHandlerMgr(); | |
| 585 pAnnotHandlerMgr->Annot_OnDraw(this, pSDKAnnot, pDevice, pUser2Device, | |
| 586 pOptions->m_bDrawAnnots); | |
| 587 } | |
| 588 } | |
| 589 | |
| 590 const CPDF_Annot* CPDFSDK_PageView::GetPDFAnnotAtPoint(FX_FLOAT pageX, | |
| 591 FX_FLOAT pageY) { | |
| 592 for (const auto& pAnnot : m_pAnnotList->All()) { | |
| 593 CFX_FloatRect annotRect = pAnnot->GetRect(); | |
| 594 if (annotRect.Contains(pageX, pageY)) | |
| 595 return pAnnot.get(); | |
| 596 } | |
| 597 return nullptr; | |
| 598 } | |
| 599 | |
| 600 const CPDF_Annot* CPDFSDK_PageView::GetPDFWidgetAtPoint(FX_FLOAT pageX, | |
| 601 FX_FLOAT pageY) { | |
| 602 for (const auto& pAnnot : m_pAnnotList->All()) { | |
| 603 if (pAnnot->GetSubtype() == CPDF_Annot::Subtype::WIDGET) { | |
| 604 CFX_FloatRect annotRect = pAnnot->GetRect(); | |
| 605 if (annotRect.Contains(pageX, pageY)) | |
| 606 return pAnnot.get(); | |
| 607 } | |
| 608 } | |
| 609 return nullptr; | |
| 610 } | |
| 611 | |
| 612 CPDFSDK_Annot* CPDFSDK_PageView::GetFXAnnotAtPoint(FX_FLOAT pageX, | |
| 613 FX_FLOAT pageY) { | |
| 614 CPDFDoc_Environment* pEnv = m_pSDKDoc->GetEnv(); | |
| 615 CPDFSDK_AnnotHandlerMgr* pAnnotMgr = pEnv->GetAnnotHandlerMgr(); | |
| 616 CPDFSDK_AnnotIterator annotIterator(this, false); | |
| 617 while (CPDFSDK_Annot* pSDKAnnot = annotIterator.Next()) { | |
| 618 CFX_FloatRect rc = pAnnotMgr->Annot_OnGetViewBBox(this, pSDKAnnot); | |
| 619 if (pSDKAnnot->GetAnnotSubtype() == CPDF_Annot::Subtype::POPUP) | |
| 620 continue; | |
| 621 if (rc.Contains(pageX, pageY)) | |
| 622 return pSDKAnnot; | |
| 623 } | |
| 624 | |
| 625 return nullptr; | |
| 626 } | |
| 627 | |
| 628 CPDFSDK_Annot* CPDFSDK_PageView::GetFXWidgetAtPoint(FX_FLOAT pageX, | |
| 629 FX_FLOAT pageY) { | |
| 630 CPDFDoc_Environment* pEnv = m_pSDKDoc->GetEnv(); | |
| 631 CPDFSDK_AnnotHandlerMgr* pAnnotMgr = pEnv->GetAnnotHandlerMgr(); | |
| 632 CPDFSDK_AnnotIterator annotIterator(this, false); | |
| 633 while (CPDFSDK_Annot* pSDKAnnot = annotIterator.Next()) { | |
| 634 bool bHitTest = pSDKAnnot->GetAnnotSubtype() == CPDF_Annot::Subtype::WIDGET; | |
| 635 #ifdef PDF_ENABLE_XFA | |
| 636 bHitTest = bHitTest || | |
| 637 pSDKAnnot->GetAnnotSubtype() == CPDF_Annot::Subtype::XFAWIDGET; | |
| 638 #endif // PDF_ENABLE_XFA | |
| 639 if (bHitTest) { | |
| 640 pAnnotMgr->Annot_OnGetViewBBox(this, pSDKAnnot); | |
| 641 CFX_FloatPoint point(pageX, pageY); | |
| 642 if (pAnnotMgr->Annot_OnHitTest(this, pSDKAnnot, point)) | |
| 643 return pSDKAnnot; | |
| 644 } | |
| 645 } | |
| 646 | |
| 647 return nullptr; | |
| 648 } | |
| 649 | |
| 650 void CPDFSDK_PageView::KillFocusAnnotIfNeeded() { | |
| 651 // if there is a focused annot on the page, we should kill the focus first. | |
| 652 if (CPDFSDK_Annot* focusedAnnot = m_pSDKDoc->GetFocusAnnot()) { | |
| 653 if (pdfium::ContainsValue(m_fxAnnotArray, focusedAnnot)) | |
| 654 KillFocusAnnot(); | |
| 655 } | |
| 656 } | |
| 657 | |
| 658 CPDFSDK_Annot* CPDFSDK_PageView::AddAnnot(CPDF_Annot* pPDFAnnot) { | |
| 659 CPDFDoc_Environment* pEnv = m_pSDKDoc->GetEnv(); | |
| 660 ASSERT(pEnv); | |
| 661 CPDFSDK_AnnotHandlerMgr* pAnnotHandler = pEnv->GetAnnotHandlerMgr(); | |
| 662 CPDFSDK_Annot* pSDKAnnot = pAnnotHandler->NewAnnot(pPDFAnnot, this); | |
| 663 if (!pSDKAnnot) | |
| 664 return nullptr; | |
| 665 | |
| 666 m_fxAnnotArray.push_back(pSDKAnnot); | |
| 667 pAnnotHandler->Annot_OnCreate(pSDKAnnot); | |
| 668 return pSDKAnnot; | |
| 669 } | |
| 670 | |
| 671 #ifdef PDF_ENABLE_XFA | |
| 672 CPDFSDK_Annot* CPDFSDK_PageView::AddAnnot(CXFA_FFWidget* pPDFAnnot) { | |
| 673 if (!pPDFAnnot) | |
| 674 return nullptr; | |
| 675 | |
| 676 CPDFSDK_Annot* pSDKAnnot = GetAnnotByXFAWidget(pPDFAnnot); | |
| 677 if (pSDKAnnot) | |
| 678 return pSDKAnnot; | |
| 679 | |
| 680 CPDFDoc_Environment* pEnv = m_pSDKDoc->GetEnv(); | |
| 681 CPDFSDK_AnnotHandlerMgr* pAnnotHandler = pEnv->GetAnnotHandlerMgr(); | |
| 682 pSDKAnnot = pAnnotHandler->NewAnnot(pPDFAnnot, this); | |
| 683 if (!pSDKAnnot) | |
| 684 return nullptr; | |
| 685 | |
| 686 m_fxAnnotArray.push_back(pSDKAnnot); | |
| 687 return pSDKAnnot; | |
| 688 } | |
| 689 #endif // PDF_ENABLE_XFA | |
| 690 | |
| 691 CPDFSDK_Annot* CPDFSDK_PageView::AddAnnot(CPDF_Dictionary* pDict) { | |
| 692 return pDict ? AddAnnot(pDict->GetStringBy("Subtype").c_str(), pDict) | |
| 693 : nullptr; | |
| 694 } | |
| 695 | |
| 696 CPDFSDK_Annot* CPDFSDK_PageView::AddAnnot(const FX_CHAR* lpSubType, | |
| 697 CPDF_Dictionary* pDict) { | |
| 698 return nullptr; | |
| 699 } | |
| 700 | |
| 701 FX_BOOL CPDFSDK_PageView::DeleteAnnot(CPDFSDK_Annot* pAnnot) { | |
| 702 #ifdef PDF_ENABLE_XFA | |
| 703 if (!pAnnot) | |
| 704 return FALSE; | |
| 705 CPDFXFA_Page* pPage = pAnnot->GetPDFXFAPage(); | |
| 706 if (!pPage || (pPage->GetDocument()->GetDocType() != DOCTYPE_STATIC_XFA && | |
| 707 pPage->GetDocument()->GetDocType() != DOCTYPE_DYNAMIC_XFA)) | |
| 708 return FALSE; | |
| 709 | |
| 710 if (GetFocusAnnot() == pAnnot) | |
| 711 KillFocusAnnot(); | |
| 712 CPDFDoc_Environment* pEnv = m_pSDKDoc->GetEnv(); | |
| 713 CPDFSDK_AnnotHandlerMgr* pAnnotHandler = pEnv->GetAnnotHandlerMgr(); | |
| 714 if (pAnnotHandler) | |
| 715 pAnnotHandler->ReleaseAnnot(pAnnot); | |
| 716 | |
| 717 auto it = std::find(m_fxAnnotArray.begin(), m_fxAnnotArray.end(), pAnnot); | |
| 718 if (it != m_fxAnnotArray.end()) | |
| 719 m_fxAnnotArray.erase(it); | |
| 720 if (m_CaptureWidget == pAnnot) | |
| 721 m_CaptureWidget = nullptr; | |
| 722 | |
| 723 return TRUE; | |
| 724 #else // PDF_ENABLE_XFA | |
| 725 return FALSE; | |
| 726 #endif // PDF_ENABLE_XFA | |
| 727 } | |
| 728 | |
| 729 CPDF_Document* CPDFSDK_PageView::GetPDFDocument() { | |
| 730 if (m_page) { | |
| 731 #ifdef PDF_ENABLE_XFA | |
| 732 return m_page->GetDocument()->GetPDFDoc(); | |
| 733 #else // PDF_ENABLE_XFA | |
| 734 return m_page->m_pDocument; | |
| 735 #endif // PDF_ENABLE_XFA | |
| 736 } | |
| 737 return nullptr; | |
| 738 } | |
| 739 | |
| 740 CPDF_Page* CPDFSDK_PageView::GetPDFPage() const { | |
| 741 #ifdef PDF_ENABLE_XFA | |
| 742 return m_page ? m_page->GetPDFPage() : nullptr; | |
| 743 #else // PDF_ENABLE_XFA | |
| 744 return m_page; | |
| 745 #endif // PDF_ENABLE_XFA | |
| 746 } | |
| 747 | |
| 748 size_t CPDFSDK_PageView::CountAnnots() const { | |
| 749 return m_fxAnnotArray.size(); | |
| 750 } | |
| 751 | |
| 752 CPDFSDK_Annot* CPDFSDK_PageView::GetAnnot(size_t nIndex) { | |
| 753 return nIndex < m_fxAnnotArray.size() ? m_fxAnnotArray[nIndex] : nullptr; | |
| 754 } | |
| 755 | |
| 756 CPDFSDK_Annot* CPDFSDK_PageView::GetAnnotByDict(CPDF_Dictionary* pDict) { | |
| 757 for (CPDFSDK_Annot* pAnnot : m_fxAnnotArray) { | |
| 758 if (pAnnot->GetPDFAnnot()->GetAnnotDict() == pDict) | |
| 759 return pAnnot; | |
| 760 } | |
| 761 return nullptr; | |
| 762 } | |
| 763 | |
| 764 #ifdef PDF_ENABLE_XFA | |
| 765 CPDFSDK_Annot* CPDFSDK_PageView::GetAnnotByXFAWidget(CXFA_FFWidget* hWidget) { | |
| 766 if (!hWidget) | |
| 767 return nullptr; | |
| 768 | |
| 769 for (CPDFSDK_Annot* pAnnot : m_fxAnnotArray) { | |
| 770 if (pAnnot->GetXFAWidget() == hWidget) | |
| 771 return pAnnot; | |
| 772 } | |
| 773 return nullptr; | |
| 774 } | |
| 775 #endif // PDF_ENABLE_XFA | |
| 776 | |
| 777 FX_BOOL CPDFSDK_PageView::OnLButtonDown(const CFX_FloatPoint& point, | |
| 778 FX_UINT nFlag) { | |
| 779 CPDFDoc_Environment* pEnv = m_pSDKDoc->GetEnv(); | |
| 780 ASSERT(pEnv); | |
| 781 CPDFSDK_Annot* pFXAnnot = GetFXWidgetAtPoint(point.x, point.y); | |
| 782 if (!pFXAnnot) { | |
| 783 KillFocusAnnot(nFlag); | |
| 784 return FALSE; | |
| 785 } | |
| 786 | |
| 787 CPDFSDK_AnnotHandlerMgr* pAnnotHandlerMgr = pEnv->GetAnnotHandlerMgr(); | |
| 788 FX_BOOL bRet = | |
| 789 pAnnotHandlerMgr->Annot_OnLButtonDown(this, pFXAnnot, nFlag, point); | |
| 790 if (bRet) | |
| 791 SetFocusAnnot(pFXAnnot); | |
| 792 return bRet; | |
| 793 } | |
| 794 | |
| 795 #ifdef PDF_ENABLE_XFA | |
| 796 FX_BOOL CPDFSDK_PageView::OnRButtonDown(const CFX_FloatPoint& point, | |
| 797 FX_UINT nFlag) { | |
| 798 CPDFDoc_Environment* pEnv = m_pSDKDoc->GetEnv(); | |
| 799 ASSERT(pEnv); | |
| 800 CPDFSDK_AnnotHandlerMgr* pAnnotHandlerMgr = pEnv->GetAnnotHandlerMgr(); | |
| 801 ASSERT(pAnnotHandlerMgr); | |
| 802 | |
| 803 CPDFSDK_Annot* pFXAnnot = GetFXWidgetAtPoint(point.x, point.y); | |
| 804 | |
| 805 if (!pFXAnnot) | |
| 806 return FALSE; | |
| 807 | |
| 808 if (pAnnotHandlerMgr->Annot_OnRButtonDown(this, pFXAnnot, nFlag, point)) | |
| 809 SetFocusAnnot(pFXAnnot); | |
| 810 | |
| 811 return TRUE; | |
| 812 } | |
| 813 | |
| 814 FX_BOOL CPDFSDK_PageView::OnRButtonUp(const CFX_FloatPoint& point, | |
| 815 FX_UINT nFlag) { | |
| 816 CPDFDoc_Environment* pEnv = m_pSDKDoc->GetEnv(); | |
| 817 ASSERT(pEnv); | |
| 818 CPDFSDK_AnnotHandlerMgr* pAnnotHandlerMgr = pEnv->GetAnnotHandlerMgr(); | |
| 819 | |
| 820 CPDFSDK_Annot* pFXAnnot = GetFXWidgetAtPoint(point.x, point.y); | |
| 821 | |
| 822 if (!pFXAnnot) | |
| 823 return FALSE; | |
| 824 | |
| 825 if (pAnnotHandlerMgr->Annot_OnRButtonUp(this, pFXAnnot, nFlag, point)) | |
| 826 SetFocusAnnot(pFXAnnot); | |
| 827 | |
| 828 return TRUE; | |
| 829 } | |
| 830 #endif // PDF_ENABLE_XFA | |
| 831 | |
| 832 FX_BOOL CPDFSDK_PageView::OnLButtonUp(const CFX_FloatPoint& point, | |
| 833 FX_UINT nFlag) { | |
| 834 CPDFDoc_Environment* pEnv = m_pSDKDoc->GetEnv(); | |
| 835 ASSERT(pEnv); | |
| 836 CPDFSDK_AnnotHandlerMgr* pAnnotHandlerMgr = pEnv->GetAnnotHandlerMgr(); | |
| 837 CPDFSDK_Annot* pFXAnnot = GetFXWidgetAtPoint(point.x, point.y); | |
| 838 CPDFSDK_Annot* pFocusAnnot = GetFocusAnnot(); | |
| 839 FX_BOOL bRet = FALSE; | |
| 840 if (pFocusAnnot && pFocusAnnot != pFXAnnot) { | |
| 841 // Last focus Annot gets a chance to handle the event. | |
| 842 bRet = pAnnotHandlerMgr->Annot_OnLButtonUp(this, pFocusAnnot, nFlag, point); | |
| 843 } | |
| 844 if (pFXAnnot && !bRet) | |
| 845 bRet = pAnnotHandlerMgr->Annot_OnLButtonUp(this, pFXAnnot, nFlag, point); | |
| 846 return bRet; | |
| 847 } | |
| 848 | |
| 849 FX_BOOL CPDFSDK_PageView::OnMouseMove(const CFX_FloatPoint& point, int nFlag) { | |
| 850 CPDFDoc_Environment* pEnv = m_pSDKDoc->GetEnv(); | |
| 851 CPDFSDK_AnnotHandlerMgr* pAnnotHandlerMgr = pEnv->GetAnnotHandlerMgr(); | |
| 852 if (CPDFSDK_Annot* pFXAnnot = GetFXAnnotAtPoint(point.x, point.y)) { | |
| 853 if (m_CaptureWidget && m_CaptureWidget != pFXAnnot) { | |
| 854 m_bExitWidget = TRUE; | |
| 855 m_bEnterWidget = FALSE; | |
| 856 pAnnotHandlerMgr->Annot_OnMouseExit(this, m_CaptureWidget, nFlag); | |
| 857 } | |
| 858 m_CaptureWidget = pFXAnnot; | |
| 859 m_bOnWidget = TRUE; | |
| 860 if (!m_bEnterWidget) { | |
| 861 m_bEnterWidget = TRUE; | |
| 862 m_bExitWidget = FALSE; | |
| 863 pAnnotHandlerMgr->Annot_OnMouseEnter(this, pFXAnnot, nFlag); | |
| 864 } | |
| 865 pAnnotHandlerMgr->Annot_OnMouseMove(this, pFXAnnot, nFlag, point); | |
| 866 return TRUE; | |
| 867 } | |
| 868 if (m_bOnWidget) { | |
| 869 m_bOnWidget = FALSE; | |
| 870 m_bExitWidget = TRUE; | |
| 871 m_bEnterWidget = FALSE; | |
| 872 if (m_CaptureWidget) { | |
| 873 pAnnotHandlerMgr->Annot_OnMouseExit(this, m_CaptureWidget, nFlag); | |
| 874 m_CaptureWidget = nullptr; | |
| 875 } | |
| 876 } | |
| 877 return FALSE; | |
| 878 } | |
| 879 | |
| 880 FX_BOOL CPDFSDK_PageView::OnMouseWheel(double deltaX, | |
| 881 double deltaY, | |
| 882 const CFX_FloatPoint& point, | |
| 883 int nFlag) { | |
| 884 if (CPDFSDK_Annot* pAnnot = GetFXWidgetAtPoint(point.x, point.y)) { | |
| 885 CPDFDoc_Environment* pEnv = m_pSDKDoc->GetEnv(); | |
| 886 CPDFSDK_AnnotHandlerMgr* pAnnotHandlerMgr = pEnv->GetAnnotHandlerMgr(); | |
| 887 return pAnnotHandlerMgr->Annot_OnMouseWheel(this, pAnnot, nFlag, | |
| 888 (int)deltaY, point); | |
| 889 } | |
| 890 return FALSE; | |
| 891 } | |
| 892 | |
| 893 FX_BOOL CPDFSDK_PageView::OnChar(int nChar, FX_UINT nFlag) { | |
| 894 if (CPDFSDK_Annot* pAnnot = GetFocusAnnot()) { | |
| 895 CPDFDoc_Environment* pEnv = m_pSDKDoc->GetEnv(); | |
| 896 CPDFSDK_AnnotHandlerMgr* pAnnotHandlerMgr = pEnv->GetAnnotHandlerMgr(); | |
| 897 return pAnnotHandlerMgr->Annot_OnChar(pAnnot, nChar, nFlag); | |
| 898 } | |
| 899 | |
| 900 return FALSE; | |
| 901 } | |
| 902 | |
| 903 FX_BOOL CPDFSDK_PageView::OnKeyDown(int nKeyCode, int nFlag) { | |
| 904 if (CPDFSDK_Annot* pAnnot = GetFocusAnnot()) { | |
| 905 CPDFDoc_Environment* pEnv = m_pSDKDoc->GetEnv(); | |
| 906 CPDFSDK_AnnotHandlerMgr* pAnnotHandlerMgr = pEnv->GetAnnotHandlerMgr(); | |
| 907 return pAnnotHandlerMgr->Annot_OnKeyDown(pAnnot, nKeyCode, nFlag); | |
| 908 } | |
| 909 return FALSE; | |
| 910 } | |
| 911 | |
| 912 FX_BOOL CPDFSDK_PageView::OnKeyUp(int nKeyCode, int nFlag) { | |
| 913 return FALSE; | |
| 914 } | |
| 915 | |
| 916 void CPDFSDK_PageView::LoadFXAnnots() { | |
| 917 CPDFDoc_Environment* pEnv = m_pSDKDoc->GetEnv(); | |
| 918 CPDFSDK_AnnotHandlerMgr* pAnnotHandlerMgr = pEnv->GetAnnotHandlerMgr(); | |
| 919 | |
| 920 SetLock(TRUE); | |
| 921 | |
| 922 #ifdef PDF_ENABLE_XFA | |
| 923 CFX_RetainPtr<CPDFXFA_Page> protector(m_page); | |
| 924 if (m_pSDKDoc->GetXFADocument()->GetDocType() == DOCTYPE_DYNAMIC_XFA) { | |
| 925 CXFA_FFPageView* pageView = m_page->GetXFAPageView(); | |
| 926 std::unique_ptr<IXFA_WidgetIterator> pWidgetHander( | |
| 927 pageView->CreateWidgetIterator( | |
| 928 XFA_TRAVERSEWAY_Form, | |
| 929 XFA_WidgetStatus_Visible | XFA_WidgetStatus_Viewable)); | |
| 930 if (!pWidgetHander) { | |
| 931 SetLock(FALSE); | |
| 932 return; | |
| 933 } | |
| 934 | |
| 935 while (CXFA_FFWidget* pXFAAnnot = pWidgetHander->MoveToNext()) { | |
| 936 CPDFSDK_Annot* pAnnot = pAnnotHandlerMgr->NewAnnot(pXFAAnnot, this); | |
| 937 if (!pAnnot) | |
| 938 continue; | |
| 939 m_fxAnnotArray.push_back(pAnnot); | |
| 940 pAnnotHandlerMgr->Annot_OnLoad(pAnnot); | |
| 941 } | |
| 942 | |
| 943 SetLock(FALSE); | |
| 944 return; | |
| 945 } | |
| 946 #endif // PDF_ENABLE_XFA | |
| 947 | |
| 948 CPDF_Page* pPage = GetPDFPage(); | |
| 949 ASSERT(pPage); | |
| 950 FX_BOOL bUpdateAP = CPDF_InterForm::IsUpdateAPEnabled(); | |
| 951 // Disable the default AP construction. | |
| 952 CPDF_InterForm::SetUpdateAP(FALSE); | |
| 953 m_pAnnotList.reset(new CPDF_AnnotList(pPage)); | |
| 954 CPDF_InterForm::SetUpdateAP(bUpdateAP); | |
| 955 | |
| 956 const size_t nCount = m_pAnnotList->Count(); | |
| 957 for (size_t i = 0; i < nCount; ++i) { | |
| 958 CPDF_Annot* pPDFAnnot = m_pAnnotList->GetAt(i); | |
| 959 CheckUnSupportAnnot(GetPDFDocument(), pPDFAnnot); | |
| 960 CPDFSDK_Annot* pAnnot = pAnnotHandlerMgr->NewAnnot(pPDFAnnot, this); | |
| 961 if (!pAnnot) | |
| 962 continue; | |
| 963 m_fxAnnotArray.push_back(pAnnot); | |
| 964 pAnnotHandlerMgr->Annot_OnLoad(pAnnot); | |
| 965 } | |
| 966 | |
| 967 SetLock(FALSE); | |
| 968 } | |
| 969 | |
| 970 void CPDFSDK_PageView::ClearFXAnnots() { | |
| 971 SetLock(TRUE); | |
| 972 if (m_pSDKDoc && GetFocusAnnot()) | |
| 973 m_pSDKDoc->SetFocusAnnot(nullptr); | |
| 974 m_CaptureWidget = nullptr; | |
| 975 for (CPDFSDK_Annot* pAnnot : m_fxAnnotArray) | |
| 976 m_pSDKDoc->GetEnv()->GetAnnotHandlerMgr()->ReleaseAnnot(pAnnot); | |
| 977 m_fxAnnotArray.clear(); | |
| 978 m_pAnnotList.reset(); | |
| 979 SetLock(FALSE); | |
| 980 } | |
| 981 | |
| 982 void CPDFSDK_PageView::UpdateRects(const std::vector<CFX_FloatRect>& rects) { | |
| 983 CPDFDoc_Environment* pEnv = m_pSDKDoc->GetEnv(); | |
| 984 for (const auto& rc : rects) | |
| 985 pEnv->FFI_Invalidate(m_page, rc.left, rc.top, rc.right, rc.bottom); | |
| 986 } | |
| 987 | |
| 988 void CPDFSDK_PageView::UpdateView(CPDFSDK_Annot* pAnnot) { | |
| 989 CFX_FloatRect rcWindow = pAnnot->GetRect(); | |
| 990 CPDFDoc_Environment* pEnv = m_pSDKDoc->GetEnv(); | |
| 991 pEnv->FFI_Invalidate(m_page, rcWindow.left, rcWindow.top, rcWindow.right, | |
| 992 rcWindow.bottom); | |
| 993 } | |
| 994 | |
| 995 int CPDFSDK_PageView::GetPageIndex() const { | |
| 996 if (!m_page) | |
| 997 return -1; | |
| 998 | |
| 999 #ifdef PDF_ENABLE_XFA | |
| 1000 int nDocType = m_page->GetDocument()->GetDocType(); | |
| 1001 switch (nDocType) { | |
| 1002 case DOCTYPE_DYNAMIC_XFA: { | |
| 1003 CXFA_FFPageView* pPageView = m_page->GetXFAPageView(); | |
| 1004 return pPageView ? pPageView->GetPageIndex() : -1; | |
| 1005 } | |
| 1006 case DOCTYPE_STATIC_XFA: | |
| 1007 case DOCTYPE_PDF: | |
| 1008 return GetPageIndexForStaticPDF(); | |
| 1009 default: | |
| 1010 return -1; | |
| 1011 } | |
| 1012 #else // PDF_ENABLE_XFA | |
| 1013 return GetPageIndexForStaticPDF(); | |
| 1014 #endif // PDF_ENABLE_XFA | |
| 1015 } | |
| 1016 | |
| 1017 bool CPDFSDK_PageView::IsValidAnnot(const CPDF_Annot* p) const { | |
| 1018 if (!p) | |
| 1019 return false; | |
| 1020 | |
| 1021 const auto& annots = m_pAnnotList->All(); | |
| 1022 auto it = std::find_if(annots.begin(), annots.end(), | |
| 1023 [p](const std::unique_ptr<CPDF_Annot>& annot) { | |
| 1024 return annot.get() == p; | |
| 1025 }); | |
| 1026 return it != annots.end(); | |
| 1027 } | |
| 1028 | |
| 1029 CPDFSDK_Annot* CPDFSDK_PageView::GetFocusAnnot() { | |
| 1030 CPDFSDK_Annot* pFocusAnnot = m_pSDKDoc->GetFocusAnnot(); | |
| 1031 if (!pFocusAnnot) | |
| 1032 return nullptr; | |
| 1033 | |
| 1034 for (CPDFSDK_Annot* pAnnot : m_fxAnnotArray) { | |
| 1035 if (pAnnot == pFocusAnnot) | |
| 1036 return pAnnot; | |
| 1037 } | |
| 1038 return nullptr; | |
| 1039 } | |
| 1040 | |
| 1041 int CPDFSDK_PageView::GetPageIndexForStaticPDF() const { | |
| 1042 CPDF_Dictionary* pDict = GetPDFPage()->m_pFormDict; | |
| 1043 CPDF_Document* pDoc = m_pSDKDoc->GetPDFDocument(); | |
| 1044 return (pDoc && pDict) ? pDoc->GetPageIndex(pDict->GetObjNum()) : -1; | |
| 1045 } | |
| OLD | NEW |