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 "xfa/src/foxitlib.h" 8 #include "xfa/src/fxfa/src/common/xfa_utils.h" 9 #include "xfa/src/fxfa/src/common/xfa_object.h" 10 #include "xfa/src/fxfa/src/common/xfa_document.h" 11 #include "xfa/src/fxfa/src/common/xfa_parser.h" 12 #include "xfa/src/fxfa/src/common/xfa_script.h" 13 #include "xfa/src/fxfa/src/common/xfa_docdata.h" 14 #include "xfa/src/fxfa/src/common/xfa_doclayout.h" 15 #include "xfa/src/fxfa/src/common/xfa_localemgr.h" 16 #include "xfa/src/fxfa/src/common/xfa_fm2jsapi.h" 17 #include "xfa_document_datamerger_imp.h" 18 #include "xfa_document_layout_imp.h" 19 #include "xfa_layout_itemlayout.h" 20 #include "xfa_layout_pagemgr_new.h" 21 #include "xfa_layout_appadapter.h" 22 CXFA_LayoutPageMgr::CXFA_LayoutPageMgr(CXFA_LayoutProcessor* pLayoutProcessor) 23 : m_pLayoutProcessor(pLayoutProcessor), 24 m_pTemplatePageSetRoot(nullptr), 25 m_pPageSetLayoutItemRoot(nullptr), 26 m_pPageSetCurRoot(nullptr), 27 m_pCurrentContainerRecord(nullptr), 28 m_pCurPageArea(nullptr), 29 m_nAvailPages(0), 30 m_nCurPageCount(0), 31 m_ePageSetMode(XFA_ATTRIBUTEENUM_OrderedOccurrence), 32 m_bCreateOverFlowPage(FALSE) { 33 } 34 CXFA_LayoutPageMgr::~CXFA_LayoutPageMgr() { 35 ClearData(); 36 CXFA_LayoutItem* pLayoutItem = GetRootLayoutItem(); 37 CXFA_LayoutItem* pNextLayout = NULL; 38 for (; pLayoutItem; pLayoutItem = pNextLayout) { 39 pNextLayout = pLayoutItem->m_pNextSibling; 40 XFA_ReleaseLayoutItem(pLayoutItem); 41 } 42 } 43 FX_BOOL CXFA_LayoutPageMgr::InitLayoutPage(CXFA_Node* pFormNode) { 44 PrepareLayout(); 45 CXFA_Node* pTemplateNode = pFormNode->GetTemplateNode(); 46 if (!pTemplateNode) { 47 return FALSE; 48 } 49 m_pTemplatePageSetRoot = pTemplateNode->GetProperty(0, XFA_ELEMENT_PageSet); 50 ASSERT(m_pTemplatePageSetRoot); 51 if (m_pPageSetLayoutItemRoot) { 52 m_pPageSetLayoutItemRoot->m_pParent = NULL; 53 m_pPageSetLayoutItemRoot->m_pFirstChild = NULL; 54 m_pPageSetLayoutItemRoot->m_pNextSibling = NULL; 55 m_pPageSetLayoutItemRoot->m_pFormNode = m_pTemplatePageSetRoot; 56 } else { 57 m_pPageSetLayoutItemRoot = 58 new CXFA_ContainerLayoutItem(m_pTemplatePageSetRoot); 59 } 60 m_pPageSetCurRoot = m_pPageSetLayoutItemRoot; 61 m_pTemplatePageSetRoot->SetUserData(XFA_LAYOUTITEMKEY, 62 (void*)m_pPageSetLayoutItemRoot); 63 XFA_ATTRIBUTEENUM eRelation = 64 m_pTemplatePageSetRoot->GetEnum(XFA_ATTRIBUTE_Relation); 65 if (eRelation != XFA_ATTRIBUTEENUM_Unknown) { 66 m_ePageSetMode = eRelation; 67 } 68 InitPageSetMap(); 69 CXFA_Node* pPageArea = NULL; 70 int32_t iCount = 0; 71 for (pPageArea = m_pTemplatePageSetRoot->GetNodeItem(XFA_NODEITEM_FirstChild); 72 pPageArea; 73 pPageArea = pPageArea->GetNodeItem(XFA_NODEITEM_NextSibling)) { 74 if (pPageArea->GetClassID() == XFA_ELEMENT_PageArea) { 75 iCount++; 76 if (pPageArea->GetFirstChildByClass(XFA_ELEMENT_ContentArea)) { 77 return TRUE; 78 } 79 } 80 } 81 if (iCount > 0) { 82 return FALSE; 83 } 84 CXFA_Document* pDocument = pTemplateNode->GetDocument(); 85 IXFA_ObjFactory* pObjFactory = pDocument->GetParser()->GetFactory(); 86 pPageArea = m_pTemplatePageSetRoot->GetChild(0, XFA_ELEMENT_PageArea); 87 if (!pPageArea) { 88 pPageArea = pObjFactory->CreateNode(m_pTemplatePageSetRoot->GetPacketID(), 89 XFA_ELEMENT_PageArea); 90 if (!pPageArea) { 91 return FALSE; 92 } 93 m_pTemplatePageSetRoot->InsertChild(pPageArea, NULL); 94 pPageArea->SetFlag(XFA_NODEFLAG_Initialized); 95 } 96 CXFA_Node* pContentArea = pPageArea->GetChild(0, XFA_ELEMENT_ContentArea); 97 if (!pContentArea) { 98 pContentArea = pObjFactory->CreateNode(pPageArea->GetPacketID(), 99 XFA_ELEMENT_ContentArea); 100 if (!pContentArea) { 101 return FALSE; 102 } 103 pPageArea->InsertChild(pContentArea, NULL); 104 pContentArea->SetFlag(XFA_NODEFLAG_Initialized); 105 pContentArea->SetMeasure(XFA_ATTRIBUTE_X, 106 CXFA_Measurement(0.25f, XFA_UNIT_In)); 107 pContentArea->SetMeasure(XFA_ATTRIBUTE_Y, 108 CXFA_Measurement(0.25f, XFA_UNIT_In)); 109 pContentArea->SetMeasure(XFA_ATTRIBUTE_W, 110 CXFA_Measurement(8.0f, XFA_UNIT_In)); 111 pContentArea->SetMeasure(XFA_ATTRIBUTE_H, 112 CXFA_Measurement(10.5f, XFA_UNIT_In)); 113 } 114 CXFA_Node* pMedium = pPageArea->GetChild(0, XFA_ELEMENT_Medium); 115 if (!pMedium) { 116 pMedium = 117 pObjFactory->CreateNode(pPageArea->GetPacketID(), XFA_ELEMENT_Medium); 118 if (!pContentArea) { 119 return FALSE; 120 } 121 pPageArea->InsertChild(pMedium, NULL); 122 pMedium->SetFlag(XFA_NODEFLAG_Initialized); 123 pMedium->SetMeasure(XFA_ATTRIBUTE_Short, 124 CXFA_Measurement(8.5f, XFA_UNIT_In)); 125 pMedium->SetMeasure(XFA_ATTRIBUTE_Long, 126 CXFA_Measurement(11.0f, XFA_UNIT_In)); 127 } 128 return TRUE; 129 } 130 FX_BOOL CXFA_LayoutPageMgr::PrepareFirstPage(CXFA_Node* pRootSubform) { 131 FX_BOOL bProBreakBefore = FALSE; 132 CXFA_Node* pBreakBeforeNode = NULL; 133 while (pRootSubform) { 134 for (CXFA_Node* pBreakNode = 135 pRootSubform->GetNodeItem(XFA_NODEITEM_FirstChild); 136 pBreakNode; 137 pBreakNode = pBreakNode->GetNodeItem(XFA_NODEITEM_NextSibling)) { 138 XFA_ELEMENT eType = pBreakNode->GetClassID(); 139 if (eType == XFA_ELEMENT_BreakBefore || 140 (eType == XFA_ELEMENT_Break && 141 pBreakNode->GetEnum(XFA_ATTRIBUTE_Before) != 142 XFA_ATTRIBUTEENUM_Auto)) { 143 bProBreakBefore = TRUE; 144 pBreakBeforeNode = pBreakNode; 145 break; 146 } 147 } 148 if (bProBreakBefore) { 149 break; 150 } 151 bProBreakBefore = TRUE; 152 pRootSubform = pRootSubform->GetFirstChildByClass(XFA_ELEMENT_Subform); 153 while (pRootSubform && 154 !XFA_ItemLayoutProcessor_IsTakingSpace(pRootSubform)) { 155 pRootSubform = pRootSubform->GetNextSameClassSibling(XFA_ELEMENT_Subform); 156 } 157 } 158 CXFA_Node *pLeader, *pTrailer; 159 if (pBreakBeforeNode && 160 ExecuteBreakBeforeOrAfter(pBreakBeforeNode, TRUE, pLeader, pTrailer)) { 161 m_pCurrentContainerRecord = m_rgProposedContainerRecord.GetHeadPosition(); 162 return TRUE; 163 } 164 return AppendNewPage(TRUE); 165 } 166 FX_BOOL CXFA_LayoutPageMgr::AppendNewPage(FX_BOOL bFirstTemPage) { 167 if (m_pCurrentContainerRecord != 168 m_rgProposedContainerRecord.GetTailPosition()) { 169 return TRUE; 170 } 171 CXFA_Node* pPageNode = GetNextAvailPageArea(NULL); 172 if (!pPageNode) { 173 return FALSE; 174 } 175 if (bFirstTemPage && m_pCurrentContainerRecord == NULL) { 176 m_pCurrentContainerRecord = m_rgProposedContainerRecord.GetHeadPosition(); 177 } 178 return !bFirstTemPage || m_pCurrentContainerRecord != NULL; 179 } 180 static void XFA_LayoutItemMgr_ReorderLayoutItemToTail( 181 CXFA_ContainerLayoutItem* pLayoutItem) { 182 CXFA_ContainerLayoutItem* pParentLayoutItem = 183 (CXFA_ContainerLayoutItem*)pLayoutItem->m_pParent; 184 if (!pParentLayoutItem) { 185 return; 186 } 187 pParentLayoutItem->RemoveChild(pLayoutItem); 188 pParentLayoutItem->AddChild(pLayoutItem); 189 } 190 static void XFA_LayoutItemMgr_RemoveLayoutItem( 191 CXFA_ContainerLayoutItem* pLayoutItem) { 192 CXFA_ContainerLayoutItem* pParentLayoutItem = 193 (CXFA_ContainerLayoutItem*)pLayoutItem->m_pParent; 194 if (!pParentLayoutItem) { 195 return; 196 } 197 pParentLayoutItem->RemoveChild(pLayoutItem); 198 } 199 void CXFA_LayoutPageMgr::RemoveLayoutRecord(CXFA_ContainerRecord* pNewRecord, 200 CXFA_ContainerRecord* pPrevRecord) { 201 if (!pNewRecord || !pPrevRecord) { 202 return; 203 } 204 if (pNewRecord->pCurPageSet != pPrevRecord->pCurPageSet) { 205 XFA_LayoutItemMgr_RemoveLayoutItem(pNewRecord->pCurPageSet); 206 return; 207 } 208 if (pNewRecord->pCurPageArea != pPrevRecord->pCurPageArea) { 209 XFA_LayoutItemMgr_RemoveLayoutItem(pNewRecord->pCurPageArea); 210 return; 211 } 212 if (pNewRecord->pCurContentArea != pPrevRecord->pCurContentArea) { 213 XFA_LayoutItemMgr_RemoveLayoutItem(pNewRecord->pCurContentArea); 214 return; 215 } 216 } 217 void CXFA_LayoutPageMgr::ReorderPendingLayoutRecordToTail( 218 CXFA_ContainerRecord* pNewRecord, 219 CXFA_ContainerRecord* pPrevRecord) { 220 if (!pNewRecord || !pPrevRecord) { 221 return; 222 } 223 if (pNewRecord->pCurPageSet != pPrevRecord->pCurPageSet) { 224 XFA_LayoutItemMgr_ReorderLayoutItemToTail(pNewRecord->pCurPageSet); 225 return; 226 } 227 if (pNewRecord->pCurPageArea != pPrevRecord->pCurPageArea) { 228 XFA_LayoutItemMgr_ReorderLayoutItemToTail(pNewRecord->pCurPageArea); 229 return; 230 } 231 if (pNewRecord->pCurContentArea != pPrevRecord->pCurContentArea) { 232 XFA_LayoutItemMgr_ReorderLayoutItemToTail(pNewRecord->pCurContentArea); 233 return; 234 } 235 } 236 void CXFA_LayoutPageMgr::SubmitContentItem( 237 CXFA_ContentLayoutItem* pContentLayoutItem, 238 XFA_ItemLayoutProcessorResult eStatus) { 239 if (pContentLayoutItem) { 240 GetCurrentContainerRecord()->pCurContentArea->AddChild(pContentLayoutItem); 241 m_bCreateOverFlowPage = FALSE; 242 } 243 if (eStatus != XFA_ItemLayoutProcessorResult_Done) { 244 if (eStatus == XFA_ItemLayoutProcessorResult_PageFullBreak && 245 m_pCurrentContainerRecord == 246 m_rgProposedContainerRecord.GetTailPosition()) { 247 AppendNewPage(); 248 } 249 m_pCurrentContainerRecord = m_rgProposedContainerRecord.GetTailPosition(); 250 m_pCurPageArea = GetCurrentContainerRecord()->pCurPageArea->m_pFormNode; 251 } 252 } 253 FX_FLOAT CXFA_LayoutPageMgr::GetAvailHeight() { 254 FX_FLOAT fAvailHeight = 255 GetCurrentContainerRecord() 256 ->pCurContentArea->m_pFormNode->GetMeasure(XFA_ATTRIBUTE_H) 257 .ToUnit(XFA_UNIT_Pt); 258 if (fAvailHeight < XFA_LAYOUT_FLOAT_PERCISION) { 259 if (m_pCurrentContainerRecord == 260 m_rgProposedContainerRecord.GetHeadPosition()) { 261 fAvailHeight = 0; 262 } else { 263 fAvailHeight = XFA_LAYOUT_FLOAT_MAX; 264 } 265 } 266 return fAvailHeight; 267 } 268 static CXFA_Node* XFA_ResolveBreakTarget(CXFA_Node* pPageSetRoot, 269 FX_BOOL bNewExprStyle, 270 CFX_WideStringC& wsTargetExpr) { 271 CXFA_Document* pDocument = pPageSetRoot->GetDocument(); 272 if (wsTargetExpr.IsEmpty()) { 273 return NULL; 274 } 275 CFX_WideString wsTargetAll = wsTargetExpr; 276 wsTargetAll.TrimLeft(); 277 wsTargetAll.TrimRight(); 278 int32_t iSpliteIndex = 0; 279 FX_BOOL bTargetAllFind = TRUE; 280 while (iSpliteIndex != -1) { 281 CFX_WideString wsTargetExpr; 282 int32_t iSpliteNextIndex = 0; 283 if (!bTargetAllFind) { 284 iSpliteNextIndex = wsTargetAll.Find(' ', iSpliteIndex); 285 wsTargetExpr = 286 wsTargetAll.Mid(iSpliteIndex, iSpliteNextIndex - iSpliteIndex); 287 } else { 288 wsTargetExpr = wsTargetAll; 289 } 290 if (wsTargetExpr.IsEmpty()) { 291 return NULL; 292 } 293 bTargetAllFind = FALSE; 294 if (wsTargetExpr.GetAt(0) == '#') { 295 CXFA_Node* pNode = pDocument->GetNodeByID( 296 (CXFA_Node*)pDocument->GetXFANode(XFA_HASHCODE_Template), 297 wsTargetExpr.Mid(1)); 298 if (pNode) { 299 return pNode; 300 } 301 } else if (bNewExprStyle) { 302 CFX_WideString wsProcessedTarget = wsTargetExpr; 303 if (wsTargetExpr.Left(4) == FX_WSTRC(L"som(") && 304 wsTargetExpr.Right(1) == FX_WSTRC(L")")) { 305 wsProcessedTarget = wsTargetExpr.Mid(4, wsTargetExpr.GetLength() - 5); 306 } 307 XFA_RESOLVENODE_RS rs; 308 int32_t iCount = pDocument->GetScriptContext()->ResolveObjects( 309 pPageSetRoot, wsProcessedTarget, rs, 310 XFA_RESOLVENODE_Children | XFA_RESOLVENODE_Properties | 311 XFA_RESOLVENODE_Attributes | XFA_RESOLVENODE_Siblings | 312 XFA_RESOLVENODE_Parent); 313 if (iCount > 0 && rs.nodes[0]->IsNode()) { 314 return (CXFA_Node*)rs.nodes[0]; 315 } 316 } 317 iSpliteIndex = iSpliteNextIndex; 318 } 319 return NULL; 320 } 321 322 FX_BOOL XFA_LayoutPageMgr_RunBreakTestScript(CXFA_Node* pTestScript) { 323 CFX_WideString wsExpression; 324 pTestScript->TryContent(wsExpression); 325 if (wsExpression.IsEmpty()) { 326 return TRUE; 327 } 328 return pTestScript->GetDocument()->GetParser()->GetNotify()->RunScript( 329 pTestScript, pTestScript->GetNodeItem(XFA_NODEITEM_Parent, 330 XFA_OBJECTTYPE_ContainerNode)); 331 } 332 CXFA_ContainerRecord* CXFA_LayoutPageMgr::CreateContainerRecord( 333 CXFA_Node* pPageNode, 334 FX_BOOL bCreateNew) { 335 CXFA_ContainerRecord* pNewRecord = new CXFA_ContainerRecord(); 336 if (m_pCurrentContainerRecord) { 337 if (!IsPageSetRootOrderedOccurrence() || pPageNode == NULL) { 338 *pNewRecord = *GetCurrentContainerRecord(); 339 m_rgProposedContainerRecord.AddTail(pNewRecord); 340 return pNewRecord; 341 } 342 CXFA_Node* pPageSet = pPageNode->GetNodeItem(XFA_NODEITEM_Parent); 343 if (!bCreateNew) { 344 if (pPageSet == m_pTemplatePageSetRoot) { 345 pNewRecord->pCurPageSet = m_pPageSetCurRoot; 346 } else { 347 CXFA_ContainerLayoutItem* pParentLayoutItem = 348 (CXFA_ContainerLayoutItem*)pPageSet->GetUserData(XFA_LAYOUTITEMKEY); 349 if (pParentLayoutItem == NULL) { 350 pParentLayoutItem = m_pPageSetCurRoot; 351 } 352 pNewRecord->pCurPageSet = pParentLayoutItem; 353 } 354 } else { 355 CXFA_ContainerLayoutItem* pParentPageSetLayout = NULL; 356 if (pPageSet == GetCurrentContainerRecord()->pCurPageSet->m_pFormNode) { 357 pParentPageSetLayout = 358 (CXFA_ContainerLayoutItem*) 359 GetCurrentContainerRecord()->pCurPageSet->m_pParent; 360 } else { 361 pParentPageSetLayout = 362 (CXFA_ContainerLayoutItem*)pPageSet->GetNodeItem( 363 XFA_NODEITEM_Parent) 364 ->GetUserData(XFA_LAYOUTITEMKEY); 365 } 366 CXFA_ContainerLayoutItem* pPageSetLayoutItem = 367 new CXFA_ContainerLayoutItem(pPageSet); 368 pPageSet->SetUserData(XFA_LAYOUTITEMKEY, (void*)pPageSetLayoutItem); 369 if (pParentPageSetLayout == NULL) { 370 CXFA_ContainerLayoutItem* pPrePageSet = m_pPageSetLayoutItemRoot; 371 while (pPrePageSet->m_pNextSibling) { 372 pPrePageSet = (CXFA_ContainerLayoutItem*)pPrePageSet->m_pNextSibling; 373 } 374 pPrePageSet->m_pNextSibling = pPageSetLayoutItem; 375 m_pPageSetCurRoot = pPageSetLayoutItem; 376 } else { 377 pParentPageSetLayout->AddChild(pPageSetLayoutItem); 378 } 379 pNewRecord->pCurPageSet = pPageSetLayoutItem; 380 } 381 } else { 382 if (pPageNode) { 383 CXFA_Node* pPageSet = pPageNode->GetNodeItem(XFA_NODEITEM_Parent); 384 if (pPageSet == m_pTemplatePageSetRoot) { 385 pNewRecord->pCurPageSet = m_pPageSetLayoutItemRoot; 386 } else { 387 CXFA_ContainerLayoutItem* pPageSetLayoutItem = 388 new CXFA_ContainerLayoutItem(pPageSet); 389 pPageSet->SetUserData(XFA_LAYOUTITEMKEY, (void*)pPageSetLayoutItem); 390 m_pPageSetLayoutItemRoot->AddChild(pPageSetLayoutItem); 391 pNewRecord->pCurPageSet = pPageSetLayoutItem; 392 } 393 } else { 394 pNewRecord->pCurPageSet = m_pPageSetLayoutItemRoot; 395 } 396 } 397 m_rgProposedContainerRecord.AddTail(pNewRecord); 398 return pNewRecord; 399 } 400 void CXFA_LayoutPageMgr::AddPageAreaLayoutItem(CXFA_ContainerRecord* pNewRecord, 401 CXFA_Node* pNewPageArea) { 402 CXFA_ContainerLayoutItem* pNewPageAreaLayoutItem = NULL; 403 if (m_PageArray.GetSize() > m_nAvailPages) { 404 CXFA_ContainerLayoutItem* pContainerItem = m_PageArray[m_nAvailPages]; 405 pContainerItem->m_pFormNode = pNewPageArea; 406 m_nAvailPages++; 407 pNewPageAreaLayoutItem = pContainerItem; 408 } else { 409 IXFA_Notify* pNotify = 410 pNewPageArea->GetDocument()->GetParser()->GetNotify(); 411 CXFA_ContainerLayoutItem* pContainerItem = 412 (CXFA_ContainerLayoutItem*)pNotify->OnCreateLayoutItem(pNewPageArea); 413 m_PageArray.Add(pContainerItem); 414 m_nAvailPages++; 415 pNotify->OnPageEvent(pContainerItem, XFA_PAGEEVENT_PageAdded, 416 (void*)(uintptr_t)m_nAvailPages); 417 pNewPageAreaLayoutItem = pContainerItem; 418 } 419 pNewRecord->pCurPageSet->AddChild(pNewPageAreaLayoutItem); 420 pNewRecord->pCurPageArea = pNewPageAreaLayoutItem; 421 pNewRecord->pCurContentArea = NULL; 422 } 423 void CXFA_LayoutPageMgr::AddContentAreaLayoutItem( 424 CXFA_ContainerRecord* pNewRecord, 425 CXFA_Node* pContentArea) { 426 if (pContentArea == NULL) { 427 pNewRecord->pCurContentArea = NULL; 428 return; 429 } 430 CXFA_ContainerLayoutItem* pNewContentAreaLayoutItem = 431 new CXFA_ContainerLayoutItem(pContentArea); 432 ASSERT(pNewRecord->pCurPageArea); 433 pNewRecord->pCurPageArea->AddChild(pNewContentAreaLayoutItem); 434 pNewRecord->pCurContentArea = pNewContentAreaLayoutItem; 435 } 436 class CXFA_TraverseStrategy_PageSetContainerLayoutItem { 437 public: 438 static inline CXFA_ContainerLayoutItem* GetFirstChild( 439 CXFA_ContainerLayoutItem* pLayoutItem) { 440 if (pLayoutItem->m_pFormNode->GetClassID() == XFA_ELEMENT_PageSet) { 441 CXFA_ContainerLayoutItem* pChildItem = 442 (CXFA_ContainerLayoutItem*)pLayoutItem->m_pFirstChild; 443 while (pChildItem && 444 pChildItem->m_pFormNode->GetClassID() != XFA_ELEMENT_PageSet) { 445 pChildItem = (CXFA_ContainerLayoutItem*)pChildItem->m_pNextSibling; 446 } 447 return pChildItem; 448 } 449 return NULL; 450 } 451 static inline CXFA_ContainerLayoutItem* GetNextSibling( 452 CXFA_ContainerLayoutItem* pLayoutItem) { 453 CXFA_ContainerLayoutItem* pChildItem = 454 (CXFA_ContainerLayoutItem*)pLayoutItem->m_pNextSibling; 455 while (pChildItem && 456 pChildItem->m_pFormNode->GetClassID() != XFA_ELEMENT_PageSet) { 457 pChildItem = (CXFA_ContainerLayoutItem*)pChildItem->m_pNextSibling; 458 } 459 return pChildItem; 460 } 461 static inline CXFA_ContainerLayoutItem* GetParent( 462 CXFA_ContainerLayoutItem* pLayoutItem) { 463 return (CXFA_ContainerLayoutItem*)pLayoutItem->m_pParent; 464 } 465 }; 466 void CXFA_LayoutPageMgr::FinishPaginatedPageSets() { 467 CXFA_ContainerLayoutItem* pRootPageSetLayoutItem = m_pPageSetLayoutItemRoot; 468 for (; pRootPageSetLayoutItem; 469 pRootPageSetLayoutItem = 470 (CXFA_ContainerLayoutItem*)pRootPageSetLayoutItem->m_pNextSibling) { 471 CXFA_NodeIteratorTemplate<CXFA_ContainerLayoutItem, 472 CXFA_TraverseStrategy_PageSetContainerLayoutItem> 473 sIterator(pRootPageSetLayoutItem); 474 for (CXFA_ContainerLayoutItem* pPageSetLayoutItem = sIterator.GetCurrent(); 475 pPageSetLayoutItem; pPageSetLayoutItem = sIterator.MoveToNext()) { 476 XFA_ATTRIBUTEENUM ePageRelation = 477 pPageSetLayoutItem->m_pFormNode->GetEnum(XFA_ATTRIBUTE_Relation); 478 switch (ePageRelation) { 479 case XFA_ATTRIBUTEENUM_OrderedOccurrence: 480 default: { ProcessLastPageSet(); } break; 481 case XFA_ATTRIBUTEENUM_SimplexPaginated: 482 case XFA_ATTRIBUTEENUM_DuplexPaginated: { 483 CXFA_LayoutItem* pLastPageAreaLayoutItem = NULL; 484 int32_t nPageAreaCount = 0; 485 for (CXFA_LayoutItem* pPageAreaLayoutItem = 486 pPageSetLayoutItem->m_pFirstChild; 487 pPageAreaLayoutItem; 488 pPageAreaLayoutItem = pPageAreaLayoutItem->m_pNextSibling) { 489 if (pPageAreaLayoutItem->m_pFormNode->GetClassID() != 490 XFA_ELEMENT_PageArea) { 491 continue; 492 } 493 nPageAreaCount++; 494 pLastPageAreaLayoutItem = pPageAreaLayoutItem; 495 } 496 if (!pLastPageAreaLayoutItem) { 497 break; 498 } 499 if (!FindPageAreaFromPageSet_SimplexDuplex( 500 pPageSetLayoutItem->m_pFormNode, NULL, NULL, NULL, TRUE, TRUE, 501 nPageAreaCount == 1 ? XFA_ATTRIBUTEENUM_Only 502 : XFA_ATTRIBUTEENUM_Last) && 503 (nPageAreaCount == 1 && 504 !FindPageAreaFromPageSet_SimplexDuplex( 505 pPageSetLayoutItem->m_pFormNode, NULL, NULL, NULL, TRUE, 506 TRUE, XFA_ATTRIBUTEENUM_Last))) { 507 break; 508 } 509 CXFA_Node* pNode = m_pCurPageArea; 510 XFA_ATTRIBUTEENUM eCurChoice = 511 pNode->GetEnum(XFA_ATTRIBUTE_PagePosition); 512 if (eCurChoice == XFA_ATTRIBUTEENUM_Last) { 513 XFA_ATTRIBUTEENUM eOddOrEven = XFA_ATTRIBUTEENUM_Any; 514 pNode->TryEnum(XFA_ATTRIBUTE_OddOrEven, eOddOrEven); 515 XFA_ATTRIBUTEENUM eLastChoice = 516 pLastPageAreaLayoutItem->m_pFormNode->GetEnum( 517 XFA_ATTRIBUTE_PagePosition); 518 if (eLastChoice == XFA_ATTRIBUTEENUM_First && 519 (ePageRelation == XFA_ATTRIBUTEENUM_SimplexPaginated || 520 eOddOrEven != XFA_ATTRIBUTEENUM_Odd)) { 521 CXFA_ContainerRecord* pRecord = CreateContainerRecord(); 522 AddPageAreaLayoutItem(pRecord, pNode); 523 break; 524 ; 525 } 526 } 527 FX_BOOL bUsable = TRUE; 528 CFX_ArrayTemplate<FX_FLOAT> rgUsedHeights; 529 for (CXFA_LayoutItem* pChildLayoutItem = 530 pLastPageAreaLayoutItem->m_pFirstChild; 531 pChildLayoutItem; 532 pChildLayoutItem = pChildLayoutItem->m_pNextSibling) { 533 if (pChildLayoutItem->m_pFormNode->GetClassID() != 534 XFA_ELEMENT_ContentArea) { 535 continue; 536 } 537 FX_FLOAT fUsedHeight = 0; 538 for (CXFA_LayoutItem* pContentChildLayoutItem = 539 pChildLayoutItem->m_pFirstChild; 540 pContentChildLayoutItem; 541 pContentChildLayoutItem = 542 pContentChildLayoutItem->m_pNextSibling) { 543 if (CXFA_ContentLayoutItem* pContent = 544 pContentChildLayoutItem->AsContentLayoutItem()) { 545 fUsedHeight += pContent->m_sSize.y; 546 } 547 } 548 rgUsedHeights.Add(fUsedHeight); 549 } 550 int32_t iCurContentAreaIndex = -1; 551 for (CXFA_Node* pContentAreaNode = 552 pNode->GetNodeItem(XFA_NODEITEM_FirstChild); 553 pContentAreaNode; 554 pContentAreaNode = 555 pContentAreaNode->GetNodeItem(XFA_NODEITEM_NextSibling)) { 556 if (pContentAreaNode->GetClassID() != XFA_ELEMENT_ContentArea) { 557 continue; 558 } 559 iCurContentAreaIndex++; 560 if (rgUsedHeights[iCurContentAreaIndex] > 561 pContentAreaNode->GetMeasure(XFA_ATTRIBUTE_H) 562 .ToUnit(XFA_UNIT_Pt) + 563 XFA_LAYOUT_FLOAT_PERCISION) { 564 bUsable = FALSE; 565 break; 566 } 567 } 568 if (bUsable) { 569 CXFA_LayoutItem* pChildLayoutItem = 570 pLastPageAreaLayoutItem->m_pFirstChild; 571 CXFA_Node* pContentAreaNode = 572 pNode->GetNodeItem(XFA_NODEITEM_FirstChild); 573 pLastPageAreaLayoutItem->m_pFormNode = pNode; 574 while (pChildLayoutItem && pContentAreaNode) { 575 if (pChildLayoutItem->m_pFormNode->GetClassID() != 576 XFA_ELEMENT_ContentArea) { 577 pChildLayoutItem = pChildLayoutItem->m_pNextSibling; 578 continue; 579 } 580 if (pContentAreaNode->GetClassID() != XFA_ELEMENT_ContentArea) { 581 pContentAreaNode = 582 pContentAreaNode->GetNodeItem(XFA_NODEITEM_NextSibling); 583 continue; 584 } 585 pChildLayoutItem->m_pFormNode = pContentAreaNode; 586 pChildLayoutItem = pChildLayoutItem->m_pNextSibling; 587 pContentAreaNode = 588 pContentAreaNode->GetNodeItem(XFA_NODEITEM_NextSibling); 589 } 590 } else if (pNode->GetEnum(XFA_ATTRIBUTE_PagePosition) == 591 XFA_ATTRIBUTEENUM_Last) { 592 CXFA_ContainerRecord* pRecord = CreateContainerRecord(); 593 AddPageAreaLayoutItem(pRecord, pNode); 594 } 595 } break; 596 } 597 } 598 } 599 } 600 int32_t CXFA_LayoutPageMgr::GetPageCount() const { 601 return m_PageArray.GetSize(); 602 } 603 IXFA_LayoutPage* CXFA_LayoutPageMgr::GetPage(int32_t index) const { 604 if (index < 0 || index >= m_PageArray.GetSize()) 605 return nullptr; 606 return m_PageArray[index]; 607 } 608 int32_t CXFA_LayoutPageMgr::GetPageIndex(const IXFA_LayoutPage* pPage) const { 609 // FIXME: Find() method should take const. 610 return m_PageArray.Find(static_cast<CXFA_ContainerLayoutItem*>( 611 const_cast<IXFA_LayoutPage*>(pPage))); 612 } 613 FX_BOOL CXFA_LayoutPageMgr::RunBreak(XFA_ELEMENT eBreakType, 614 XFA_ATTRIBUTEENUM eTargetType, 615 CXFA_Node* pTarget, 616 FX_BOOL bStartNew) { 617 FX_BOOL bRet = FALSE; 618 switch (eTargetType) { 619 case XFA_ATTRIBUTEENUM_ContentArea: 620 if (pTarget && pTarget->GetClassID() != XFA_ELEMENT_ContentArea) { 621 pTarget = NULL; 622 } 623 if (!pTarget || !m_pCurrentContainerRecord || 624 pTarget != 625 GetCurrentContainerRecord()->pCurContentArea->m_pFormNode || 626 bStartNew) { 627 CXFA_Node* pPageArea = NULL; 628 if (pTarget) { 629 pPageArea = pTarget->GetNodeItem(XFA_NODEITEM_Parent); 630 } 631 pPageArea = GetNextAvailPageArea(pPageArea, pTarget); 632 bRet = pPageArea != NULL; 633 } 634 break; 635 case XFA_ATTRIBUTEENUM_PageArea: 636 if (pTarget && pTarget->GetClassID() != XFA_ELEMENT_PageArea) { 637 pTarget = NULL; 638 } 639 if (!pTarget || !m_pCurrentContainerRecord || 640 pTarget != GetCurrentContainerRecord()->pCurPageArea->m_pFormNode || 641 bStartNew) { 642 CXFA_Node* pPageArea = GetNextAvailPageArea(pTarget, NULL, TRUE); 643 bRet = pPageArea != NULL; 644 } 645 break; 646 case XFA_ATTRIBUTEENUM_PageOdd: 647 if (pTarget && pTarget->GetClassID() != XFA_ELEMENT_PageArea) { 648 pTarget = NULL; 649 } 650 if (m_nAvailPages % 2 != 1 || !m_pCurrentContainerRecord || 651 (pTarget && 652 pTarget != GetCurrentContainerRecord()->pCurPageArea->m_pFormNode) || 653 bStartNew) { 654 if (m_nAvailPages % 2 == 1) { 655 } 656 } 657 break; 658 case XFA_ATTRIBUTEENUM_PageEven: 659 if (pTarget && pTarget->GetClassID() != XFA_ELEMENT_PageArea) { 660 pTarget = NULL; 661 } 662 if (m_nAvailPages % 2 != 0 || !m_pCurrentContainerRecord || 663 (pTarget && 664 pTarget != GetCurrentContainerRecord()->pCurPageArea->m_pFormNode) || 665 bStartNew) { 666 if (m_nAvailPages % 2 == 0) { 667 } 668 } 669 break; 670 case XFA_ATTRIBUTEENUM_Auto: 671 default: 672 break; 673 ; 674 } 675 return bRet; 676 } 677 FX_BOOL CXFA_LayoutPageMgr::ExecuteBreakBeforeOrAfter( 678 CXFA_Node* pCurNode, 679 FX_BOOL bBefore, 680 CXFA_Node*& pBreakLeaderTemplate, 681 CXFA_Node*& pBreakTrailerTemplate) { 682 XFA_ELEMENT eType = pCurNode->GetClassID(); 683 switch (eType) { 684 case XFA_ELEMENT_BreakBefore: 685 case XFA_ELEMENT_BreakAfter: { 686 CFX_WideStringC wsBreakLeader, wsBreakTrailer; 687 CXFA_Node* pFormNode = pCurNode->GetNodeItem( 688 XFA_NODEITEM_Parent, XFA_OBJECTTYPE_ContainerNode); 689 CXFA_Node* pContainer = pFormNode->GetTemplateNode(); 690 FX_BOOL bStartNew = pCurNode->GetInteger(XFA_ATTRIBUTE_StartNew) != 0; 691 CXFA_Node* pScript = pCurNode->GetFirstChildByClass(XFA_ELEMENT_Script); 692 if (pScript && !XFA_LayoutPageMgr_RunBreakTestScript(pScript)) { 693 return FALSE; 694 } 695 CFX_WideStringC wsTarget = pCurNode->GetCData(XFA_ATTRIBUTE_Target); 696 CXFA_Node* pTarget = 697 XFA_ResolveBreakTarget(m_pTemplatePageSetRoot, TRUE, wsTarget); 698 wsBreakTrailer = pCurNode->GetCData(XFA_ATTRIBUTE_Trailer); 699 wsBreakLeader = pCurNode->GetCData(XFA_ATTRIBUTE_Leader); 700 pBreakLeaderTemplate = 701 XFA_ResolveBreakTarget(pContainer, TRUE, wsBreakLeader); 702 pBreakTrailerTemplate = 703 XFA_ResolveBreakTarget(pContainer, TRUE, wsBreakTrailer); 704 if (RunBreak(eType, pCurNode->GetEnum(XFA_ATTRIBUTE_TargetType), pTarget, 705 bStartNew)) { 706 return TRUE; 707 } else { 708 if (m_rgProposedContainerRecord.GetCount() > 0 && 709 m_pCurrentContainerRecord == 710 m_rgProposedContainerRecord.GetHeadPosition() && 711 eType == XFA_ELEMENT_BreakBefore) { 712 CXFA_Node* pParentNode = pFormNode->GetNodeItem( 713 XFA_NODEITEM_Parent, XFA_OBJECTTYPE_ContainerNode); 714 if (!pParentNode || 715 pFormNode != 716 pParentNode->GetNodeItem(XFA_NODEITEM_FirstChild, 717 XFA_OBJECTTYPE_ContainerNode)) { 718 break; 719 } 720 pParentNode = pParentNode->GetNodeItem(XFA_NODEITEM_Parent); 721 if (!pParentNode || pParentNode->GetClassID() != XFA_ELEMENT_Form) { 722 break; 723 } 724 return TRUE; 725 } 726 } 727 } break; 728 case XFA_ELEMENT_Break: { 729 FX_BOOL bStartNew = pCurNode->GetInteger(XFA_ATTRIBUTE_StartNew) != 0; 730 CFX_WideStringC wsTarget = pCurNode->GetCData( 731 bBefore ? XFA_ATTRIBUTE_BeforeTarget : XFA_ATTRIBUTE_AfterTarget); 732 CXFA_Node* pTarget = 733 XFA_ResolveBreakTarget(m_pTemplatePageSetRoot, TRUE, wsTarget); 734 if (RunBreak(bBefore ? XFA_ELEMENT_BreakBefore : XFA_ELEMENT_BreakAfter, 735 pCurNode->GetEnum(bBefore ? XFA_ATTRIBUTE_Before 736 : XFA_ATTRIBUTE_After), 737 pTarget, bStartNew)) { 738 return TRUE; 739 } 740 } break; 741 default: 742 break; 743 } 744 return FALSE; 745 } 746 static void XFA_SetLayoutGeneratedNodeFlag(CXFA_Node* pNode) { 747 pNode->SetFlag(XFA_NODEFLAG_LayoutGeneratedNode, TRUE, FALSE); 748 pNode->SetFlag(XFA_NODEFLAG_UnusedNode, FALSE, FALSE); 749 } 750 FX_BOOL CXFA_LayoutPageMgr::ProcessBreakBeforeOrAfter( 751 CXFA_Node* pBreakNode, 752 FX_BOOL bBefore, 753 CXFA_Node*& pBreakLeaderNode, 754 CXFA_Node*& pBreakTrailerNode, 755 FX_BOOL& bCreatePage) { 756 CXFA_Node *pLeaderTemplate = NULL, *pTrailerTemplate = NULL; 757 CXFA_Node* pFormNode = pBreakNode->GetNodeItem(XFA_NODEITEM_Parent, 758 XFA_OBJECTTYPE_ContainerNode); 759 if (XFA_ItemLayoutProcessor_IsTakingSpace(pFormNode)) { 760 bCreatePage = ExecuteBreakBeforeOrAfter(pBreakNode, bBefore, 761 pLeaderTemplate, pTrailerTemplate); 762 CXFA_Document* pDocument = pBreakNode->GetDocument(); 763 CXFA_Node* pDataScope = NULL; 764 pFormNode = pFormNode->GetNodeItem(XFA_NODEITEM_Parent, 765 XFA_OBJECTTYPE_ContainerNode); 766 if (pLeaderTemplate) { 767 if (!pDataScope) { 768 pDataScope = XFA_DataMerge_FindDataScope(pFormNode); 769 } 770 pBreakLeaderNode = pDocument->DataMerge_CopyContainer( 771 pLeaderTemplate, pFormNode, pDataScope, TRUE); 772 pDocument->DataMerge_UpdateBindingRelations(pBreakLeaderNode); 773 XFA_SetLayoutGeneratedNodeFlag(pBreakLeaderNode); 774 } 775 if (pTrailerTemplate) { 776 if (!pDataScope) { 777 pDataScope = XFA_DataMerge_FindDataScope(pFormNode); 778 } 779 pBreakTrailerNode = pDocument->DataMerge_CopyContainer( 780 pTrailerTemplate, pFormNode, pDataScope, TRUE); 781 pDocument->DataMerge_UpdateBindingRelations(pBreakTrailerNode); 782 XFA_SetLayoutGeneratedNodeFlag(pBreakTrailerNode); 783 } 784 return TRUE; 785 } 786 return FALSE; 787 } 788 FX_BOOL CXFA_LayoutPageMgr::ProcessBookendLeaderOrTrailer( 789 CXFA_Node* pBookendNode, 790 FX_BOOL bLeader, 791 CXFA_Node*& pBookendAppendNode) { 792 CXFA_Node* pLeaderTemplate = NULL; 793 CXFA_Node* pFormNode = pBookendNode->GetNodeItem( 794 XFA_NODEITEM_Parent, XFA_OBJECTTYPE_ContainerNode); 795 if (ResolveBookendLeaderOrTrailer(pBookendNode, bLeader, pLeaderTemplate)) { 796 CXFA_Document* pDocument = pBookendNode->GetDocument(); 797 CXFA_Node* pDataScope = NULL; 798 if (pLeaderTemplate) { 799 if (!pDataScope) { 800 pDataScope = XFA_DataMerge_FindDataScope(pFormNode); 801 } 802 pBookendAppendNode = pDocument->DataMerge_CopyContainer( 803 pLeaderTemplate, pFormNode, pDataScope, TRUE); 804 pDocument->DataMerge_UpdateBindingRelations(pBookendAppendNode); 805 XFA_SetLayoutGeneratedNodeFlag(pBookendAppendNode); 806 return TRUE; 807 } 808 } 809 return FALSE; 810 } 811 CXFA_Node* CXFA_LayoutPageMgr::BreakOverflow(CXFA_Node* pOverflowNode, 812 CXFA_Node*& pLeaderTemplate, 813 CXFA_Node*& pTrailerTemplate, 814 FX_BOOL bCreatePage) { 815 CFX_WideStringC wsOverflowLeader, wsOverflowTrailer; 816 CXFA_Node* pContainer = 817 pOverflowNode->GetNodeItem(XFA_NODEITEM_Parent, 818 XFA_OBJECTTYPE_ContainerNode) 819 ->GetTemplateNode(); 820 if (pOverflowNode->GetClassID() == XFA_ELEMENT_Break) { 821 CFX_WideStringC wsOverflowLeader; 822 CFX_WideStringC wsOverflowTarget; 823 CFX_WideStringC wsOverflowTrailer; 824 pOverflowNode->TryCData(XFA_ATTRIBUTE_OverflowLeader, wsOverflowLeader); 825 pOverflowNode->TryCData(XFA_ATTRIBUTE_OverflowTrailer, wsOverflowTrailer); 826 pOverflowNode->TryCData(XFA_ATTRIBUTE_OverflowTarget, wsOverflowTarget); 827 if (!wsOverflowLeader.IsEmpty() || !wsOverflowTrailer.IsEmpty() || 828 !wsOverflowTarget.IsEmpty()) { 829 if (!wsOverflowTarget.IsEmpty() && bCreatePage && 830 !m_bCreateOverFlowPage) { 831 CXFA_Node* pTarget = XFA_ResolveBreakTarget( 832 this->m_pTemplatePageSetRoot, TRUE, wsOverflowTarget); 833 if (pTarget) { 834 m_bCreateOverFlowPage = TRUE; 835 switch (pTarget->GetClassID()) { 836 case XFA_ELEMENT_PageArea: 837 RunBreak(XFA_ELEMENT_Overflow, XFA_ATTRIBUTEENUM_PageArea, 838 pTarget, TRUE); 839 break; 840 case XFA_ELEMENT_ContentArea: 841 RunBreak(XFA_ELEMENT_Overflow, XFA_ATTRIBUTEENUM_ContentArea, 842 pTarget, TRUE); 843 break; 844 default: 845 break; 846 } 847 } 848 } 849 if (!bCreatePage) { 850 pLeaderTemplate = 851 XFA_ResolveBreakTarget(pContainer, TRUE, wsOverflowLeader); 852 pTrailerTemplate = 853 XFA_ResolveBreakTarget(pContainer, TRUE, wsOverflowTrailer); 854 } 855 return pOverflowNode; 856 } 857 return NULL; 858 } else if (pOverflowNode->GetClassID() == XFA_ELEMENT_Overflow) { 859 CFX_WideStringC wsOverflowTarget; 860 pOverflowNode->TryCData(XFA_ATTRIBUTE_Leader, wsOverflowLeader); 861 pOverflowNode->TryCData(XFA_ATTRIBUTE_Trailer, wsOverflowTrailer); 862 pOverflowNode->TryCData(XFA_ATTRIBUTE_Target, wsOverflowTarget); 863 if (!wsOverflowTarget.IsEmpty() && bCreatePage && !m_bCreateOverFlowPage) { 864 CXFA_Node* pTarget = XFA_ResolveBreakTarget(this->m_pTemplatePageSetRoot, 865 TRUE, wsOverflowTarget); 866 if (pTarget) { 867 m_bCreateOverFlowPage = TRUE; 868 switch (pTarget->GetClassID()) { 869 case XFA_ELEMENT_PageArea: 870 RunBreak(XFA_ELEMENT_Overflow, XFA_ATTRIBUTEENUM_PageArea, pTarget, 871 TRUE); 872 break; 873 case XFA_ELEMENT_ContentArea: 874 RunBreak(XFA_ELEMENT_Overflow, XFA_ATTRIBUTEENUM_ContentArea, 875 pTarget, TRUE); 876 break; 877 default: 878 break; 879 } 880 } 881 } 882 if (!bCreatePage) { 883 pLeaderTemplate = 884 XFA_ResolveBreakTarget(pContainer, TRUE, wsOverflowLeader); 885 pTrailerTemplate = 886 XFA_ResolveBreakTarget(pContainer, TRUE, wsOverflowTrailer); 887 } 888 return pOverflowNode; 889 } 890 return NULL; 891 } 892 FX_BOOL CXFA_LayoutPageMgr::ProcessOverflow(CXFA_Node* pFormNode, 893 CXFA_Node*& pLeaderNode, 894 CXFA_Node*& pTrailerNode, 895 FX_BOOL bDataMerge, 896 FX_BOOL bCreatePage) { 897 if (pFormNode == NULL) { 898 return FALSE; 899 } 900 CXFA_Node *pLeaderTemplate = NULL, *pTrailerTemplate = NULL; 901 FX_BOOL bIsOverflowNode = FALSE; 902 if (pFormNode->GetClassID() == XFA_ELEMENT_Overflow || 903 pFormNode->GetClassID() == XFA_ELEMENT_Break) { 904 bIsOverflowNode = TRUE; 905 } 906 for (CXFA_Node* pCurNode = 907 bIsOverflowNode ? pFormNode 908 : pFormNode->GetNodeItem(XFA_NODEITEM_FirstChild); 909 pCurNode; pCurNode = pCurNode->GetNodeItem((XFA_NODEITEM_NextSibling))) { 910 if (BreakOverflow(pCurNode, pLeaderTemplate, pTrailerTemplate, 911 bCreatePage)) { 912 if (bIsOverflowNode) { 913 pFormNode = pCurNode->GetNodeItem(XFA_NODEITEM_Parent); 914 } 915 CXFA_Document* pDocument = pCurNode->GetDocument(); 916 CXFA_Node* pDataScope = NULL; 917 if (pLeaderTemplate) { 918 if (!pDataScope) { 919 pDataScope = XFA_DataMerge_FindDataScope(pFormNode); 920 } 921 pLeaderNode = pDocument->DataMerge_CopyContainer( 922 pLeaderTemplate, pFormNode, pDataScope, TRUE); 923 pDocument->DataMerge_UpdateBindingRelations(pLeaderNode); 924 XFA_SetLayoutGeneratedNodeFlag(pLeaderNode); 925 } 926 if (pTrailerTemplate) { 927 if (!pDataScope) { 928 pDataScope = XFA_DataMerge_FindDataScope(pFormNode); 929 } 930 pTrailerNode = pDocument->DataMerge_CopyContainer( 931 pTrailerTemplate, pFormNode, pDataScope, TRUE); 932 pDocument->DataMerge_UpdateBindingRelations(pTrailerNode); 933 XFA_SetLayoutGeneratedNodeFlag(pTrailerNode); 934 } 935 return TRUE; 936 } 937 if (bIsOverflowNode) { 938 break; 939 } 940 } 941 return FALSE; 942 } 943 FX_BOOL CXFA_LayoutPageMgr::ResolveBookendLeaderOrTrailer( 944 CXFA_Node* pBookendNode, 945 FX_BOOL bLeader, 946 CXFA_Node*& pBookendAppendTemplate) { 947 CFX_WideStringC wsBookendLeader; 948 CXFA_Node* pContainer = 949 pBookendNode->GetNodeItem(XFA_NODEITEM_Parent, 950 XFA_OBJECTTYPE_ContainerNode) 951 ->GetTemplateNode(); 952 if (pBookendNode->GetClassID() == XFA_ELEMENT_Break) { 953 pBookendNode->TryCData( 954 bLeader ? XFA_ATTRIBUTE_BookendLeader : XFA_ATTRIBUTE_BookendTrailer, 955 wsBookendLeader); 956 if (!wsBookendLeader.IsEmpty()) { 957 pBookendAppendTemplate = 958 XFA_ResolveBreakTarget(pContainer, FALSE, wsBookendLeader); 959 return TRUE; 960 } 961 return FALSE; 962 } else if (pBookendNode->GetClassID() == XFA_ELEMENT_Bookend) { 963 pBookendNode->TryCData( 964 bLeader ? XFA_ATTRIBUTE_Leader : XFA_ATTRIBUTE_Trailer, 965 wsBookendLeader); 966 pBookendAppendTemplate = 967 XFA_ResolveBreakTarget(pContainer, TRUE, wsBookendLeader); 968 return TRUE; 969 } 970 return FALSE; 971 } 972 FX_BOOL CXFA_LayoutPageMgr::FindPageAreaFromPageSet( 973 CXFA_Node* pPageSet, 974 CXFA_Node* pStartChild, 975 CXFA_Node* pTargetPageArea, 976 CXFA_Node* pTargetContentArea, 977 FX_BOOL bNewPage, 978 FX_BOOL bQuery) { 979 if (pPageSet == NULL && pStartChild == NULL) { 980 return FALSE; 981 } 982 if (IsPageSetRootOrderedOccurrence()) { 983 return FindPageAreaFromPageSet_Ordered(pPageSet, pStartChild, 984 pTargetPageArea, pTargetContentArea, 985 bNewPage, bQuery); 986 } 987 XFA_ATTRIBUTEENUM ePreferredPosition = m_pCurrentContainerRecord 988 ? XFA_ATTRIBUTEENUM_Rest 989 : XFA_ATTRIBUTEENUM_First; 990 return FindPageAreaFromPageSet_SimplexDuplex( 991 pPageSet, pStartChild, pTargetPageArea, pTargetContentArea, bNewPage, 992 bQuery, ePreferredPosition); 993 } 994 FX_BOOL CXFA_LayoutPageMgr::FindPageAreaFromPageSet_Ordered( 995 CXFA_Node* pPageSet, 996 CXFA_Node* pStartChild, 997 CXFA_Node* pTargetPageArea, 998 CXFA_Node* pTargetContentArea, 999 FX_BOOL bNewPage, 1000 FX_BOOL bQuery) { 1001 int32_t iPageSetCount = 0; 1002 if (!pStartChild && !bQuery) { 1003 m_pPageSetMap.Lookup(pPageSet, iPageSetCount); 1004 int32_t iMax = -1; 1005 CXFA_Node* pOccurNode = pPageSet->GetFirstChildByClass(XFA_ELEMENT_Occur); 1006 if (pOccurNode) { 1007 pOccurNode->TryInteger(XFA_ATTRIBUTE_Max, iMax, FALSE); 1008 } 1009 if (iMax >= 0 && iMax <= iPageSetCount) { 1010 return FALSE; 1011 } 1012 } 1013 FX_BOOL bRes = FALSE; 1014 CXFA_Node* pCurrentNode = 1015 pStartChild ? pStartChild->GetNodeItem(XFA_NODEITEM_NextSibling) 1016 : pPageSet->GetNodeItem(XFA_NODEITEM_FirstChild); 1017 for (; pCurrentNode; 1018 pCurrentNode = pCurrentNode->GetNodeItem(XFA_NODEITEM_NextSibling)) { 1019 if (pCurrentNode->GetClassID() == XFA_ELEMENT_PageArea) { 1020 if ((pTargetPageArea == pCurrentNode || pTargetPageArea == NULL)) { 1021 if (pCurrentNode->GetFirstChildByClass(XFA_ELEMENT_ContentArea) == 1022 NULL) { 1023 if (pTargetPageArea == pCurrentNode) { 1024 CreateMinPageRecord(pCurrentNode, TRUE); 1025 pTargetPageArea = NULL; 1026 } 1027 continue; 1028 } 1029 if (!bQuery) { 1030 CXFA_ContainerRecord* pNewRecord = 1031 CreateContainerRecord(pCurrentNode, pStartChild == NULL); 1032 AddPageAreaLayoutItem(pNewRecord, pCurrentNode); 1033 if (pTargetContentArea == NULL) { 1034 pTargetContentArea = 1035 pCurrentNode->GetFirstChildByClass(XFA_ELEMENT_ContentArea); 1036 } 1037 AddContentAreaLayoutItem(pNewRecord, pTargetContentArea); 1038 } 1039 m_pCurPageArea = pCurrentNode; 1040 m_nCurPageCount = 1; 1041 bRes = TRUE; 1042 break; 1043 } 1044 if (!bQuery) { 1045 CreateMinPageRecord(pCurrentNode, FALSE); 1046 } 1047 } else if (pCurrentNode->GetClassID() == XFA_ELEMENT_PageSet) { 1048 if (FindPageAreaFromPageSet_Ordered(pCurrentNode, NULL, pTargetPageArea, 1049 pTargetContentArea, bNewPage, 1050 bQuery)) { 1051 bRes = TRUE; 1052 break; 1053 } 1054 if (!bQuery) { 1055 CreateMinPageSetRecord(pCurrentNode, TRUE); 1056 } 1057 } 1058 } 1059 if (!pStartChild && bRes && !bQuery) { 1060 m_pPageSetMap.SetAt(pPageSet, ++iPageSetCount); 1061 } 1062 return bRes; 1063 } 1064 FX_BOOL CXFA_LayoutPageMgr::FindPageAreaFromPageSet_SimplexDuplex( 1065 CXFA_Node* pPageSet, 1066 CXFA_Node* pStartChild, 1067 CXFA_Node* pTargetPageArea, 1068 CXFA_Node* pTargetContentArea, 1069 FX_BOOL bNewPage, 1070 FX_BOOL bQuery, 1071 XFA_ATTRIBUTEENUM ePreferredPosition) { 1072 const XFA_ATTRIBUTEENUM eFallbackPosition = XFA_ATTRIBUTEENUM_Any; 1073 CXFA_Node *pPreferredPageArea = NULL, *pFallbackPageArea = NULL; 1074 CXFA_Node* pCurrentNode = NULL; 1075 if (!pStartChild || pStartChild->GetClassID() == XFA_ELEMENT_PageArea) { 1076 pCurrentNode = pPageSet->GetNodeItem(XFA_NODEITEM_FirstChild); 1077 } else { 1078 pCurrentNode = pStartChild->GetNodeItem(XFA_NODEITEM_NextSibling); 1079 } 1080 for (; pCurrentNode; 1081 pCurrentNode = pCurrentNode->GetNodeItem(XFA_NODEITEM_NextSibling)) { 1082 if (pCurrentNode->GetClassID() == XFA_ELEMENT_PageArea) { 1083 if (!MatchPageAreaOddOrEven(pCurrentNode, FALSE)) { 1084 continue; 1085 } 1086 XFA_ATTRIBUTEENUM eCurPagePosition = 1087 pCurrentNode->GetEnum(XFA_ATTRIBUTE_PagePosition); 1088 if (ePreferredPosition == XFA_ATTRIBUTEENUM_Last) { 1089 if (eCurPagePosition != ePreferredPosition) { 1090 continue; 1091 } 1092 if (m_ePageSetMode == XFA_ATTRIBUTEENUM_SimplexPaginated || 1093 pCurrentNode->GetEnum(XFA_ATTRIBUTE_OddOrEven) == 1094 XFA_ATTRIBUTEENUM_Any) { 1095 pPreferredPageArea = pCurrentNode; 1096 break; 1097 } 1098 CXFA_ContainerRecord* pNewRecord = CreateContainerRecord(); 1099 AddPageAreaLayoutItem(pNewRecord, pCurrentNode); 1100 AddContentAreaLayoutItem(pNewRecord, pCurrentNode->GetFirstChildByClass( 1101 XFA_ELEMENT_ContentArea)); 1102 pPreferredPageArea = pCurrentNode; 1103 return FALSE; 1104 } else if (ePreferredPosition == XFA_ATTRIBUTEENUM_Only) { 1105 if (eCurPagePosition != ePreferredPosition) { 1106 continue; 1107 } 1108 if (m_ePageSetMode != XFA_ATTRIBUTEENUM_DuplexPaginated || 1109 pCurrentNode->GetEnum(XFA_ATTRIBUTE_OddOrEven) == 1110 XFA_ATTRIBUTEENUM_Any) { 1111 pPreferredPageArea = pCurrentNode; 1112 break; 1113 } 1114 return FALSE; 1115 } 1116 if ((pTargetPageArea == pCurrentNode || pTargetPageArea == NULL)) { 1117 if (pCurrentNode->GetFirstChildByClass(XFA_ELEMENT_ContentArea) == 1118 NULL) { 1119 if (pTargetPageArea == pCurrentNode) { 1120 CXFA_ContainerRecord* pNewRecord = CreateContainerRecord(); 1121 AddPageAreaLayoutItem(pNewRecord, pCurrentNode); 1122 pTargetPageArea = NULL; 1123 } 1124 continue; 1125 } 1126 if ((ePreferredPosition == XFA_ATTRIBUTEENUM_Rest && 1127 eCurPagePosition == XFA_ATTRIBUTEENUM_Any) || 1128 eCurPagePosition == ePreferredPosition) { 1129 pPreferredPageArea = pCurrentNode; 1130 break; 1131 } else if (eCurPagePosition == eFallbackPosition && 1132 !pFallbackPageArea) { 1133 pFallbackPageArea = pCurrentNode; 1134 } 1135 } else if (pTargetPageArea && 1136 !MatchPageAreaOddOrEven(pTargetPageArea, FALSE)) { 1137 CXFA_ContainerRecord* pNewRecord = CreateContainerRecord(); 1138 AddPageAreaLayoutItem(pNewRecord, pCurrentNode); 1139 AddContentAreaLayoutItem(pNewRecord, pCurrentNode->GetFirstChildByClass( 1140 XFA_ELEMENT_ContentArea)); 1141 } 1142 } else if (pCurrentNode->GetClassID() == XFA_ELEMENT_PageSet) { 1143 if (FindPageAreaFromPageSet_SimplexDuplex( 1144 pCurrentNode, NULL, pTargetPageArea, pTargetContentArea, bNewPage, 1145 bQuery, ePreferredPosition)) { 1146 break; 1147 } 1148 } 1149 } 1150 CXFA_Node* pCurPageArea = NULL; 1151 if (pPreferredPageArea) { 1152 pCurPageArea = pPreferredPageArea; 1153 } else if (pFallbackPageArea) { 1154 pCurPageArea = pFallbackPageArea; 1155 } 1156 if (!pCurPageArea) { 1157 return FALSE; 1158 } 1159 if (!bQuery) { 1160 CXFA_ContainerRecord* pNewRecord = CreateContainerRecord(); 1161 AddPageAreaLayoutItem(pNewRecord, pCurPageArea); 1162 if (pTargetContentArea == NULL) { 1163 pTargetContentArea = 1164 pCurPageArea->GetFirstChildByClass(XFA_ELEMENT_ContentArea); 1165 } 1166 AddContentAreaLayoutItem(pNewRecord, pTargetContentArea); 1167 } 1168 m_pCurPageArea = pCurPageArea; 1169 return TRUE; 1170 } 1171 FX_BOOL CXFA_LayoutPageMgr::MatchPageAreaOddOrEven(CXFA_Node* pPageArea, 1172 FX_BOOL bLastMatch) { 1173 if (m_ePageSetMode != XFA_ATTRIBUTEENUM_DuplexPaginated) { 1174 return TRUE; 1175 } 1176 XFA_ATTRIBUTEENUM eOddOrEven = XFA_ATTRIBUTEENUM_Any; 1177 pPageArea->TryEnum(XFA_ATTRIBUTE_OddOrEven, eOddOrEven); 1178 if (eOddOrEven != XFA_ATTRIBUTEENUM_Any) { 1179 int32_t iPageCount = GetPageCount(); 1180 if (bLastMatch) { 1181 return eOddOrEven == XFA_ATTRIBUTEENUM_Odd ? iPageCount % 2 == 1 1182 : iPageCount % 2 == 0; 1183 } 1184 return eOddOrEven == XFA_ATTRIBUTEENUM_Odd ? iPageCount % 2 == 0 1185 : iPageCount % 2 == 1; 1186 } 1187 return TRUE; 1188 } 1189 CXFA_Node* CXFA_LayoutPageMgr::GetNextAvailPageArea( 1190 CXFA_Node* pTargetPageArea, 1191 CXFA_Node* pTargetContentArea, 1192 FX_BOOL bNewPage, 1193 FX_BOOL bQuery) { 1194 if (m_pCurPageArea == NULL) { 1195 FindPageAreaFromPageSet(m_pTemplatePageSetRoot, NULL, pTargetPageArea, 1196 pTargetContentArea, bNewPage, bQuery); 1197 ASSERT(m_pCurPageArea); 1198 return m_pCurPageArea; 1199 } 1200 if (pTargetPageArea == NULL || pTargetPageArea == m_pCurPageArea) { 1201 if (!bNewPage && GetNextContentArea(pTargetContentArea)) { 1202 return m_pCurPageArea; 1203 } 1204 if (IsPageSetRootOrderedOccurrence()) { 1205 int32_t iMax = -1; 1206 CXFA_Node* pOccurNode = 1207 m_pCurPageArea->GetFirstChildByClass(XFA_ELEMENT_Occur); 1208 if (pOccurNode) { 1209 pOccurNode->TryInteger(XFA_ATTRIBUTE_Max, iMax, FALSE); 1210 } 1211 if ((iMax < 0 || m_nCurPageCount < iMax)) { 1212 if (!bQuery) { 1213 CXFA_ContainerRecord* pNewRecord = 1214 CreateContainerRecord(m_pCurPageArea); 1215 AddPageAreaLayoutItem(pNewRecord, m_pCurPageArea); 1216 if (pTargetContentArea == NULL) { 1217 pTargetContentArea = 1218 m_pCurPageArea->GetFirstChildByClass(XFA_ELEMENT_ContentArea); 1219 } 1220 AddContentAreaLayoutItem(pNewRecord, pTargetContentArea); 1221 } 1222 m_nCurPageCount++; 1223 return m_pCurPageArea; 1224 } 1225 } 1226 } 1227 if (!bQuery && IsPageSetRootOrderedOccurrence()) { 1228 CreateMinPageRecord(m_pCurPageArea, FALSE, TRUE); 1229 } 1230 if (FindPageAreaFromPageSet(m_pCurPageArea->GetNodeItem(XFA_NODEITEM_Parent), 1231 m_pCurPageArea, pTargetPageArea, 1232 pTargetContentArea, bNewPage, bQuery)) { 1233 return m_pCurPageArea; 1234 } 1235 CXFA_Node* pPageSet = m_pCurPageArea->GetNodeItem(XFA_NODEITEM_Parent); 1236 while (TRUE) { 1237 if (FindPageAreaFromPageSet(pPageSet, NULL, pTargetPageArea, 1238 pTargetContentArea, bNewPage, bQuery)) { 1239 return m_pCurPageArea; 1240 } 1241 if (!bQuery && IsPageSetRootOrderedOccurrence()) { 1242 CreateMinPageSetRecord(pPageSet); 1243 } 1244 if (FindPageAreaFromPageSet(NULL, pPageSet, pTargetPageArea, 1245 pTargetContentArea, bNewPage, bQuery)) { 1246 return m_pCurPageArea; 1247 } 1248 if (pPageSet == m_pTemplatePageSetRoot) { 1249 break; 1250 } 1251 pPageSet = pPageSet->GetNodeItem(XFA_NODEITEM_Parent); 1252 } 1253 return NULL; 1254 } 1255 static FX_BOOL XFA_LayoutPageMgr_CheckContentAreaNotUsed( 1256 CXFA_ContainerLayoutItem* pPageAreaLayoutItem, 1257 CXFA_Node* pContentArea, 1258 CXFA_ContainerLayoutItem*& pContentAreaLayoutItem) { 1259 for (CXFA_ContainerLayoutItem* pLayoutItem = 1260 (CXFA_ContainerLayoutItem*)pPageAreaLayoutItem->m_pFirstChild; 1261 pLayoutItem; 1262 pLayoutItem = (CXFA_ContainerLayoutItem*)pLayoutItem->m_pNextSibling) { 1263 if (pLayoutItem->m_pFormNode == pContentArea) { 1264 if (pLayoutItem->m_pFirstChild == NULL) { 1265 pContentAreaLayoutItem = pLayoutItem; 1266 return TRUE; 1267 } 1268 return FALSE; 1269 } 1270 } 1271 return TRUE; 1272 } 1273 FX_BOOL CXFA_LayoutPageMgr::GetNextContentArea(CXFA_Node* pContentArea) { 1274 CXFA_Node* pCurContentNode = 1275 GetCurrentContainerRecord()->pCurContentArea->m_pFormNode; 1276 if (pContentArea == NULL) { 1277 pContentArea = 1278 pCurContentNode->GetNextSameClassSibling(XFA_ELEMENT_ContentArea); 1279 if (pContentArea == NULL) { 1280 return FALSE; 1281 } 1282 } else { 1283 if (pContentArea->GetNodeItem(XFA_NODEITEM_Parent) != m_pCurPageArea) { 1284 return FALSE; 1285 } 1286 CXFA_ContainerLayoutItem* pContentAreaLayout = NULL; 1287 if (!XFA_LayoutPageMgr_CheckContentAreaNotUsed( 1288 GetCurrentContainerRecord()->pCurPageArea, pContentArea, 1289 pContentAreaLayout)) { 1290 return FALSE; 1291 } 1292 if (pContentAreaLayout) { 1293 if (pContentAreaLayout->m_pFormNode != pCurContentNode) { 1294 CXFA_ContainerRecord* pNewRecord = CreateContainerRecord(); 1295 pNewRecord->pCurContentArea = pContentAreaLayout; 1296 return TRUE; 1297 } else { 1298 return FALSE; 1299 } 1300 } 1301 } 1302 CXFA_ContainerRecord* pNewRecord = CreateContainerRecord(); 1303 AddContentAreaLayoutItem(pNewRecord, pContentArea); 1304 return TRUE; 1305 } 1306 void CXFA_LayoutPageMgr::InitPageSetMap() { 1307 if (!IsPageSetRootOrderedOccurrence()) { 1308 return; 1309 } 1310 CXFA_NodeIterator sIterator(m_pTemplatePageSetRoot); 1311 for (CXFA_Node* pPageSetNode = sIterator.GetCurrent(); pPageSetNode; 1312 pPageSetNode = sIterator.MoveToNext()) { 1313 if (pPageSetNode->GetClassID() == XFA_ELEMENT_PageSet) { 1314 XFA_ATTRIBUTEENUM eRelation = 1315 pPageSetNode->GetEnum(XFA_ATTRIBUTE_Relation); 1316 if (eRelation == XFA_ATTRIBUTEENUM_OrderedOccurrence) { 1317 m_pPageSetMap.SetAt(pPageSetNode, 0); 1318 } 1319 } 1320 } 1321 } 1322 int32_t CXFA_LayoutPageMgr::CreateMinPageRecord(CXFA_Node* pPageArea, 1323 FX_BOOL bTargetPageArea, 1324 FX_BOOL bCreateLast) { 1325 if (pPageArea == NULL) { 1326 return 0; 1327 } 1328 CXFA_Node* pOccurNode = pPageArea->GetFirstChildByClass(XFA_ELEMENT_Occur); 1329 int32_t iMin = 0; 1330 if ((pOccurNode && pOccurNode->TryInteger(XFA_ATTRIBUTE_Min, iMin, FALSE)) || 1331 bTargetPageArea) { 1332 CXFA_Node* pContentArea = 1333 pPageArea->GetFirstChildByClass(XFA_ELEMENT_ContentArea); 1334 if (iMin < 1 && bTargetPageArea && !pContentArea) { 1335 iMin = 1; 1336 } 1337 int32_t i = 0; 1338 if (bCreateLast) { 1339 i = m_nCurPageCount; 1340 } 1341 for (; i < iMin; i++) { 1342 CXFA_ContainerRecord* pNewRecord = CreateContainerRecord(); 1343 AddPageAreaLayoutItem(pNewRecord, pPageArea); 1344 AddContentAreaLayoutItem(pNewRecord, pContentArea); 1345 } 1346 } 1347 return iMin; 1348 } 1349 void CXFA_LayoutPageMgr::CreateMinPageSetRecord(CXFA_Node* pPageSet, 1350 FX_BOOL bCreateAll) { 1351 if (pPageSet == NULL) { 1352 return; 1353 } 1354 int32_t iCurSetCount = 0; 1355 if (!m_pPageSetMap.Lookup(pPageSet, iCurSetCount)) { 1356 return; 1357 } 1358 if (bCreateAll) { 1359 iCurSetCount = 0; 1360 } 1361 CXFA_Node* pOccurNode = pPageSet->GetFirstChildByClass(XFA_ELEMENT_Occur); 1362 int32_t iMin = 0; 1363 if (pOccurNode && pOccurNode->TryInteger(XFA_ATTRIBUTE_Min, iMin, FALSE)) { 1364 if (iCurSetCount < iMin) { 1365 for (int32_t i = 0; i < iMin - iCurSetCount; i++) { 1366 for (CXFA_Node* pCurrentPageNode = 1367 pPageSet->GetNodeItem(XFA_NODEITEM_FirstChild); 1368 pCurrentPageNode; pCurrentPageNode = pCurrentPageNode->GetNodeItem( 1369 XFA_NODEITEM_NextSibling)) { 1370 if (pCurrentPageNode->GetClassID() == XFA_ELEMENT_PageArea) { 1371 CreateMinPageRecord(pCurrentPageNode, FALSE); 1372 } else if (pCurrentPageNode->GetClassID() == XFA_ELEMENT_PageSet) { 1373 CreateMinPageSetRecord(pCurrentPageNode, TRUE); 1374 } 1375 } 1376 } 1377 m_pPageSetMap.SetAt(pPageSet, iMin); 1378 } 1379 } 1380 } 1381 void CXFA_LayoutPageMgr::CreateNextMinRecord(CXFA_Node* pRecordNode) { 1382 if (pRecordNode == NULL) { 1383 return; 1384 } 1385 for (CXFA_Node* pCurrentNode = 1386 pRecordNode->GetNodeItem(XFA_NODEITEM_NextSibling); 1387 pCurrentNode; 1388 pCurrentNode = pCurrentNode->GetNodeItem(XFA_NODEITEM_NextSibling)) { 1389 if (pCurrentNode->GetClassID() == XFA_ELEMENT_PageArea) { 1390 CreateMinPageRecord(pCurrentNode, FALSE); 1391 } else if (pCurrentNode->GetClassID() == XFA_ELEMENT_PageSet) { 1392 CreateMinPageSetRecord(pCurrentNode, TRUE); 1393 } 1394 } 1395 } 1396 void CXFA_LayoutPageMgr::ProcessLastPageSet() { 1397 CreateMinPageRecord(m_pCurPageArea, FALSE, TRUE); 1398 CreateNextMinRecord(m_pCurPageArea); 1399 CXFA_Node* pPageSet = m_pCurPageArea->GetNodeItem(XFA_NODEITEM_Parent); 1400 while (TRUE) { 1401 CreateMinPageSetRecord(pPageSet); 1402 if (pPageSet == m_pTemplatePageSetRoot) { 1403 break; 1404 } 1405 CreateNextMinRecord(pPageSet); 1406 pPageSet = pPageSet->GetNodeItem(XFA_NODEITEM_Parent); 1407 } 1408 } 1409 FX_BOOL CXFA_LayoutPageMgr::GetNextAvailContentHeight(FX_FLOAT fChildHeight) { 1410 CXFA_Node* pCurContentNode = 1411 GetCurrentContainerRecord()->pCurContentArea->m_pFormNode; 1412 if (pCurContentNode == NULL) { 1413 return FALSE; 1414 } 1415 pCurContentNode = 1416 pCurContentNode->GetNextSameClassSibling(XFA_ELEMENT_ContentArea); 1417 if (pCurContentNode) { 1418 FX_FLOAT fNextContentHeight = 1419 pCurContentNode->GetMeasure(XFA_ATTRIBUTE_H).ToUnit(XFA_UNIT_Pt); 1420 return fNextContentHeight > fChildHeight; 1421 } 1422 CXFA_Node* pPageNode = GetCurrentContainerRecord()->pCurPageArea->m_pFormNode; 1423 CXFA_Node* pOccurNode = pPageNode->GetFirstChildByClass(XFA_ELEMENT_Occur); 1424 int32_t iMax = 0; 1425 if (pOccurNode && pOccurNode->TryInteger(XFA_ATTRIBUTE_Max, iMax, FALSE)) { 1426 if (m_nCurPageCount == iMax) { 1427 CXFA_Node* pSrcPage = m_pCurPageArea; 1428 int32_t nSrcPageCount = m_nCurPageCount; 1429 FX_POSITION psSrcRecord = m_rgProposedContainerRecord.GetTailPosition(); 1430 CXFA_Node* pNextPage = GetNextAvailPageArea(NULL, NULL, FALSE, TRUE); 1431 m_pCurPageArea = pSrcPage; 1432 m_nCurPageCount = nSrcPageCount; 1433 CXFA_ContainerRecord* pPrevRecord = 1434 (CXFA_ContainerRecord*)m_rgProposedContainerRecord.GetNext( 1435 psSrcRecord); 1436 while (psSrcRecord) { 1437 FX_POSITION psSaveRecord = psSrcRecord; 1438 CXFA_ContainerRecord* pInsertRecord = 1439 (CXFA_ContainerRecord*)m_rgProposedContainerRecord.GetNext( 1440 psSrcRecord); 1441 RemoveLayoutRecord(pInsertRecord, pPrevRecord); 1442 delete pInsertRecord; 1443 m_rgProposedContainerRecord.RemoveAt(psSaveRecord); 1444 } 1445 if (pNextPage) { 1446 CXFA_Node* pContentArea = 1447 pNextPage->GetFirstChildByClass(XFA_ELEMENT_ContentArea); 1448 if (pContentArea) { 1449 FX_FLOAT fNextContentHeight = 1450 pContentArea->GetMeasure(XFA_ATTRIBUTE_H).ToUnit(XFA_UNIT_Pt); 1451 if (fNextContentHeight > fChildHeight) { 1452 return TRUE; 1453 } 1454 } 1455 } 1456 return FALSE; 1457 } 1458 } 1459 CXFA_Node* pContentArea = 1460 pPageNode->GetFirstChildByClass(XFA_ELEMENT_ContentArea); 1461 FX_FLOAT fNextContentHeight = 1462 pContentArea->GetMeasure(XFA_ATTRIBUTE_H).ToUnit(XFA_UNIT_Pt); 1463 if (fNextContentHeight < XFA_LAYOUT_FLOAT_PERCISION) { 1464 return TRUE; 1465 } 1466 if (fNextContentHeight > fChildHeight) { 1467 return TRUE; 1468 } 1469 return FALSE; 1470 } 1471 void CXFA_LayoutPageMgr::ClearData() { 1472 ClearRecordList(); 1473 } 1474 void CXFA_LayoutPageMgr::ClearRecordList() { 1475 if (!m_pTemplatePageSetRoot) { 1476 return; 1477 } 1478 if (m_rgProposedContainerRecord.GetCount() > 0) { 1479 FX_POSITION sPos; 1480 sPos = m_rgProposedContainerRecord.GetHeadPosition(); 1481 while (sPos) { 1482 CXFA_ContainerRecord* pRecord = 1483 (CXFA_ContainerRecord*)m_rgProposedContainerRecord.GetNext(sPos); 1484 delete pRecord; 1485 } 1486 m_rgProposedContainerRecord.RemoveAll(); 1487 } 1488 m_pCurrentContainerRecord = NULL; 1489 m_pCurPageArea = NULL; 1490 m_nCurPageCount = 0; 1491 m_bCreateOverFlowPage = FALSE; 1492 m_pPageSetMap.RemoveAll(); 1493 } 1494 CXFA_LayoutItem* CXFA_LayoutPageMgr::FindOrCreateLayoutItem( 1495 CXFA_Node* pFormNode) { 1496 #if defined(_XFA_LAYOUTITEM_MAPCACHE_) 1497 if (m_NodeToContent.GetCount() > 0) { 1498 CXFA_ContentLayoutItem* pLayoutItem = NULL; 1499 if (m_NodeToContent.Lookup(pFormNode, (void*&)pLayoutItem)) { 1500 if (pLayoutItem->m_pNext) { 1501 m_NodeToContent.SetAt(pFormNode, pLayoutItem->m_pNext); 1502 pLayoutItem->m_pNext->m_pPrev = NULL; 1503 pLayoutItem->m_pNext = NULL; 1504 } else { 1505 m_NodeToContent.RemoveKey(pFormNode); 1506 } 1507 pLayoutItem->m_pFormNode = pFormNode; 1508 return pLayoutItem; 1509 } 1510 } 1511 #endif 1512 return (CXFA_LayoutItem*)pFormNode->GetDocument() 1513 ->GetParser() 1514 ->GetNotify() 1515 ->OnCreateLayoutItem(pFormNode); 1516 } 1517 #if defined(_XFA_LAYOUTITEM_MAPCACHE_) 1518 void CXFA_LayoutPageMgr::SaveLayoutItem(CXFA_LayoutItem* pParentLayoutItem) { 1519 CXFA_LayoutItem* pNextLayoutItem, 1520 * pCurLayoutItem = pParentLayoutItem->m_pFirstChild; 1521 while (pCurLayoutItem) { 1522 pNextLayoutItem = pCurLayoutItem->m_pNextSibling; 1523 if (pCurLayoutItem->m_pFirstChild) { 1524 SaveLayoutItem(pCurLayoutItem); 1525 } 1526 if (pCurLayoutItem->IsContentLayoutItem()) { 1527 if (m_NodeToContent.GetValueAt(pCurLayoutItem->m_pFormNode) == NULL) { 1528 pCurLayoutItem->m_pFormNode->SetUserData(XFA_LAYOUTITEMKEY, NULL); 1529 m_NodeToContent.SetAt(pCurLayoutItem->m_pFormNode, pCurLayoutItem); 1530 } 1531 } else if (pCurLayoutItem->m_pFormNode->GetClassID() != 1532 XFA_ELEMENT_PageArea) { 1533 delete pCurLayoutItem; 1534 pCurLayoutItem = NULL; 1535 } 1536 if (pCurLayoutItem) { 1537 pCurLayoutItem->m_pParent = NULL; 1538 pCurLayoutItem->m_pNextSibling = NULL; 1539 pCurLayoutItem->m_pFirstChild = NULL; 1540 } 1541 pCurLayoutItem = pNextLayoutItem; 1542 } 1543 } 1544 #elif defined(_XFA_LAYOUTITEM_ProcessCACHE_) 1545 static void XFA_SyncRemoveLayoutItem(CXFA_LayoutItem* pParentLayoutItem, 1546 IXFA_Notify* pNotify, 1547 IXFA_DocLayout* pDocLayout) { 1548 CXFA_LayoutItem* pNextLayoutItem; 1549 CXFA_LayoutItem* pCurLayoutItem = pParentLayoutItem->m_pFirstChild; 1550 while (pCurLayoutItem) { 1551 pNextLayoutItem = pCurLayoutItem->m_pNextSibling; 1552 if (pCurLayoutItem->m_pFirstChild) { 1553 XFA_SyncRemoveLayoutItem(pCurLayoutItem, pNotify, pDocLayout); 1554 } 1555 pNotify->OnLayoutEvent(pDocLayout, pCurLayoutItem, 1556 XFA_LAYOUTEVENT_ItemRemoving); 1557 delete pCurLayoutItem; 1558 pCurLayoutItem = pNextLayoutItem; 1559 } 1560 } 1561 void CXFA_LayoutPageMgr::SaveLayoutItem(CXFA_LayoutItem* pParentLayoutItem) { 1562 CXFA_LayoutItem* pNextLayoutItem; 1563 CXFA_LayoutItem* pCurLayoutItem = pParentLayoutItem->m_pFirstChild; 1564 while (pCurLayoutItem) { 1565 pNextLayoutItem = pCurLayoutItem->m_pNextSibling; 1566 if (pCurLayoutItem->IsContentLayoutItem()) { 1567 FX_DWORD dwFlag = pCurLayoutItem->m_pFormNode->GetFlag(); 1568 if (dwFlag & (XFA_NODEFLAG_HasRemoved)) { 1569 IXFA_Notify* pNotify = 1570 m_pTemplatePageSetRoot->GetDocument()->GetParser()->GetNotify(); 1571 IXFA_DocLayout* pDocLayout = 1572 m_pTemplatePageSetRoot->GetDocument()->GetDocLayout(); 1573 if (pCurLayoutItem->m_pFirstChild) { 1574 XFA_SyncRemoveLayoutItem(pCurLayoutItem, pNotify, pDocLayout); 1575 } 1576 pNotify->OnLayoutEvent(pDocLayout, pCurLayoutItem, 1577 XFA_LAYOUTEVENT_ItemRemoving); 1578 delete pCurLayoutItem; 1579 pCurLayoutItem = pNextLayoutItem; 1580 continue; 1581 } 1582 if (dwFlag & XFA_NODEFLAG_LayoutGeneratedNode) { 1583 CXFA_NodeIteratorTemplate<CXFA_Node, CXFA_TraverseStrategy_XFANode> 1584 sIterator(pCurLayoutItem->m_pFormNode); 1585 for (CXFA_Node* pNode = sIterator.GetCurrent(); pNode; 1586 pNode = sIterator.MoveToNext()) { 1587 pNode->SetFlag(XFA_NODEFLAG_UnusedNode, TRUE, FALSE); 1588 } 1589 } 1590 } 1591 if (pCurLayoutItem->m_pFirstChild) { 1592 SaveLayoutItem(pCurLayoutItem); 1593 } 1594 pCurLayoutItem->m_pParent = NULL; 1595 pCurLayoutItem->m_pNextSibling = NULL; 1596 pCurLayoutItem->m_pFirstChild = NULL; 1597 if (!pCurLayoutItem->IsContentLayoutItem() && 1598 pCurLayoutItem->m_pFormNode->GetClassID() != XFA_ELEMENT_PageArea) { 1599 delete pCurLayoutItem; 1600 } 1601 pCurLayoutItem = pNextLayoutItem; 1602 } 1603 } 1604 #endif 1605 CXFA_Node* CXFA_LayoutPageMgr::QueryOverflow( 1606 CXFA_Node* pFormNode, 1607 CXFA_LayoutContext* pLayoutContext) { 1608 for (CXFA_Node* pCurNode = pFormNode->GetNodeItem(XFA_NODEITEM_FirstChild); 1609 pCurNode; pCurNode = pCurNode->GetNodeItem((XFA_NODEITEM_NextSibling))) { 1610 if (pCurNode->GetClassID() == XFA_ELEMENT_Break) { 1611 CFX_WideStringC wsOverflowLeader; 1612 CFX_WideStringC wsOverflowTarget; 1613 CFX_WideStringC wsOverflowTrailer; 1614 pCurNode->TryCData(XFA_ATTRIBUTE_OverflowLeader, wsOverflowLeader); 1615 pCurNode->TryCData(XFA_ATTRIBUTE_OverflowTrailer, wsOverflowTrailer); 1616 pCurNode->TryCData(XFA_ATTRIBUTE_OverflowTarget, wsOverflowTarget); 1617 if (!wsOverflowLeader.IsEmpty() || !wsOverflowTrailer.IsEmpty() || 1618 !wsOverflowTarget.IsEmpty()) { 1619 return pCurNode; 1620 } 1621 return NULL; 1622 } else if (pCurNode->GetClassID() == XFA_ELEMENT_Overflow) { 1623 return pCurNode; 1624 } 1625 } 1626 return NULL; 1627 } 1628 void CXFA_LayoutPageMgr::MergePageSetContents() { 1629 CXFA_Document* pDocument = m_pTemplatePageSetRoot->GetDocument(); 1630 IXFA_Notify* pNotify = pDocument->GetParser()->GetNotify(); 1631 IXFA_DocLayout* pDocLayout = pDocument->GetDocLayout(); 1632 CXFA_ContainerLayoutItem* pRootLayout = this->GetRootLayoutItem(); 1633 { 1634 for (int32_t iIndex = 0; iIndex < pDocument->m_pPendingPageSet.GetSize(); 1635 iIndex++) { 1636 CXFA_NodeIteratorTemplate<CXFA_Node, CXFA_TraverseStrategy_XFANode> 1637 sIterator(pDocument->m_pPendingPageSet.GetAt(iIndex)); 1638 for (CXFA_Node* pNode = sIterator.GetCurrent(); pNode; 1639 pNode = sIterator.MoveToNext()) { 1640 if (pNode->IsContainerNode()) { 1641 CXFA_Node* pBindNode = pNode->GetBindData(); 1642 if (pBindNode) { 1643 pBindNode->RemoveBindItem(pNode); 1644 pNode->SetObject(XFA_ATTRIBUTE_BindingNode, NULL); 1645 } 1646 } 1647 pNode->SetFlag(XFA_NODEFLAG_UnusedNode); 1648 } 1649 } 1650 } 1651 int32_t iIndex = 0; 1652 CXFA_Node* pPendingPageSet = NULL; 1653 for (; pRootLayout; 1654 pRootLayout = (CXFA_ContainerLayoutItem*)pRootLayout->m_pNextSibling) { 1655 pPendingPageSet = NULL; 1656 CXFA_NodeIteratorTemplate< 1657 CXFA_ContainerLayoutItem, 1658 CXFA_TraverseStrategy_ContentAreaContainerLayoutItem> 1659 iterator(pRootLayout); 1660 CXFA_ContainerLayoutItem* pRootPageSetContainerItem = iterator.GetCurrent(); 1661 ASSERT(pRootPageSetContainerItem->m_pFormNode->GetClassID() == 1662 XFA_ELEMENT_PageSet); 1663 if (iIndex < pDocument->m_pPendingPageSet.GetSize()) { 1664 pPendingPageSet = pDocument->m_pPendingPageSet.GetAt(iIndex); 1665 iIndex++; 1666 } 1667 if (!pPendingPageSet) { 1668 if (pRootPageSetContainerItem->m_pFormNode->GetPacketID() == 1669 XFA_XDPPACKET_Template) { 1670 pPendingPageSet = 1671 pRootPageSetContainerItem->m_pFormNode->CloneTemplateToForm(FALSE); 1672 } else { 1673 pPendingPageSet = pRootPageSetContainerItem->m_pFormNode; 1674 } 1675 } 1676 if (pRootPageSetContainerItem->m_pFormNode->GetUserData( 1677 XFA_LAYOUTITEMKEY) == pRootPageSetContainerItem) { 1678 pRootPageSetContainerItem->m_pFormNode->SetUserData(XFA_LAYOUTITEMKEY, 1679 NULL); 1680 } 1681 pRootPageSetContainerItem->m_pFormNode = pPendingPageSet; 1682 pPendingPageSet->SetFlag(XFA_NODEFLAG_UnusedNode, FALSE); 1683 for (CXFA_ContainerLayoutItem* pContainerItem = iterator.MoveToNext(); 1684 pContainerItem; pContainerItem = iterator.MoveToNext()) { 1685 CXFA_Node* pNode = pContainerItem->m_pFormNode; 1686 if (pNode->GetPacketID() != XFA_XDPPACKET_Template) { 1687 continue; 1688 } 1689 switch (pNode->GetClassID()) { 1690 case XFA_ELEMENT_PageSet: { 1691 CXFA_Node* pParentNode = pContainerItem->m_pParent->m_pFormNode; 1692 pContainerItem->m_pFormNode = XFA_NodeMerge_CloneOrMergeContainer( 1693 pDocument, pParentNode, pContainerItem->m_pFormNode, TRUE); 1694 } break; 1695 case XFA_ELEMENT_PageArea: { 1696 CXFA_ContainerLayoutItem* pFormLayout = pContainerItem; 1697 CXFA_Node* pParentNode = pContainerItem->m_pParent->m_pFormNode; 1698 FX_BOOL bIsExistForm = TRUE; 1699 for (int32_t iLevel = 0; iLevel < 3; iLevel++) { 1700 pFormLayout = (CXFA_ContainerLayoutItem*)pFormLayout->m_pFirstChild; 1701 if (iLevel == 2) { 1702 while (pFormLayout && 1703 !XFA_ItemLayoutProcessor_IsTakingSpace( 1704 pFormLayout->m_pFormNode)) { 1705 pFormLayout = 1706 (CXFA_ContainerLayoutItem*)pFormLayout->m_pNextSibling; 1707 } 1708 } 1709 if (pFormLayout == NULL) { 1710 bIsExistForm = FALSE; 1711 break; 1712 } 1713 } 1714 if (bIsExistForm) { 1715 CXFA_Node* pNewSubform = pFormLayout->m_pFormNode; 1716 if (pContainerItem->m_pOldSubform != NULL && 1717 pContainerItem->m_pOldSubform != pNewSubform) { 1718 CXFA_Node* pExistingNode = XFA_DataMerge_FindFormDOMInstance( 1719 pDocument, pContainerItem->m_pFormNode->GetClassID(), 1720 pContainerItem->m_pFormNode->GetNameHash(), pParentNode); 1721 CXFA_ContainerIterator sIterator(pExistingNode); 1722 for (CXFA_Node* pNode = sIterator.GetCurrent(); pNode; 1723 pNode = sIterator.MoveToNext()) { 1724 if (pNode->GetClassID() != XFA_ELEMENT_ContentArea) { 1725 CXFA_LayoutItem* pLayoutItem = static_cast<CXFA_LayoutItem*>( 1726 pNode->GetUserData(XFA_LAYOUTITEMKEY)); 1727 if (pLayoutItem) { 1728 pNotify->OnLayoutEvent(pDocLayout, pLayoutItem, 1729 XFA_LAYOUTEVENT_ItemRemoving); 1730 delete pLayoutItem; 1731 } 1732 } 1733 } 1734 if (pExistingNode) { 1735 pParentNode->RemoveChild(pExistingNode); 1736 } 1737 } 1738 pContainerItem->m_pOldSubform = pNewSubform; 1739 } 1740 pContainerItem->m_pFormNode = pDocument->DataMerge_CopyContainer( 1741 pContainerItem->m_pFormNode, pParentNode, 1742 (CXFA_Node*)pDocument->GetXFANode(XFA_HASHCODE_Record), TRUE); 1743 } break; 1744 case XFA_ELEMENT_ContentArea: { 1745 CXFA_Node* pParentNode = pContainerItem->m_pParent->m_pFormNode; 1746 for (CXFA_Node* pChildNode = 1747 pParentNode->GetNodeItem(XFA_NODEITEM_FirstChild); 1748 pChildNode; 1749 pChildNode = pChildNode->GetNodeItem(XFA_NODEITEM_NextSibling)) { 1750 if (pChildNode->GetTemplateNode() != pContainerItem->m_pFormNode) { 1751 continue; 1752 } 1753 pContainerItem->m_pFormNode = pChildNode; 1754 break; 1755 } 1756 } break; 1757 default: 1758 break; 1759 } 1760 } 1761 if (!pPendingPageSet->GetNodeItem(XFA_NODEITEM_Parent)) { 1762 CXFA_Node* pFormToplevelSubform = 1763 ((CXFA_Node*)pDocument->GetXFANode(XFA_HASHCODE_Form)) 1764 ->GetFirstChildByClass(XFA_ELEMENT_Subform); 1765 pFormToplevelSubform->InsertChild(pPendingPageSet); 1766 } 1767 pDocument->DataMerge_UpdateBindingRelations(pPendingPageSet); 1768 pPendingPageSet->SetFlag(XFA_NODEFLAG_Initialized); 1769 } 1770 pPendingPageSet = GetRootLayoutItem()->m_pFormNode; 1771 while (pPendingPageSet) { 1772 CXFA_Node* pNextPendingPageSet = 1773 pPendingPageSet->GetNextSameClassSibling(XFA_ELEMENT_PageSet); 1774 CXFA_NodeIteratorTemplate<CXFA_Node, CXFA_TraverseStrategy_XFANode> 1775 sIterator(pPendingPageSet); 1776 CXFA_Node* pNode = sIterator.GetCurrent(); 1777 while (pNode) { 1778 if (pNode->HasFlag(XFA_NODEFLAG_UnusedNode)) { 1779 if (pNode->GetObjectType() == XFA_OBJECTTYPE_ContainerNode) { 1780 XFA_ELEMENT eCurId = pNode->GetClassID(); 1781 if (eCurId == XFA_ELEMENT_PageArea || eCurId == XFA_ELEMENT_PageSet) { 1782 CXFA_ContainerIterator iteChild(pNode); 1783 CXFA_Node* pChildNode = iteChild.MoveToNext(); 1784 for (; pChildNode; pChildNode = iteChild.MoveToNext()) { 1785 CXFA_LayoutItem* pLayoutItem = static_cast<CXFA_LayoutItem*>( 1786 pChildNode->GetUserData(XFA_LAYOUTITEMKEY)); 1787 if (pLayoutItem) { 1788 pNotify->OnLayoutEvent(pDocLayout, pLayoutItem, 1789 XFA_LAYOUTEVENT_ItemRemoving); 1790 delete pLayoutItem; 1791 } 1792 } 1793 } else if (eCurId != XFA_ELEMENT_ContentArea) { 1794 CXFA_LayoutItem* pLayoutItem = static_cast<CXFA_LayoutItem*>( 1795 pNode->GetUserData(XFA_LAYOUTITEMKEY)); 1796 if (pLayoutItem) { 1797 pNotify->OnLayoutEvent(pDocLayout, pLayoutItem, 1798 XFA_LAYOUTEVENT_ItemRemoving); 1799 delete pLayoutItem; 1800 } 1801 } 1802 CXFA_Node* pNext = sIterator.SkipChildrenAndMoveToNext(); 1803 pNode->GetNodeItem(XFA_NODEITEM_Parent)->RemoveChild(pNode); 1804 pNode = pNext; 1805 } else { 1806 pNode->SetFlag(XFA_NODEFLAG_UnusedNode, FALSE); 1807 pNode->SetFlag(XFA_NODEFLAG_Initialized); 1808 pNode = sIterator.MoveToNext(); 1809 } 1810 } else { 1811 pNode->SetFlag(XFA_NODEFLAG_Initialized); 1812 pNode = sIterator.MoveToNext(); 1813 } 1814 } 1815 pPendingPageSet = pNextPendingPageSet; 1816 } 1817 } 1818 void CXFA_LayoutPageMgr::LayoutPageSetContents() { 1819 CXFA_ContainerLayoutItem* pRootLayoutItem = this->GetRootLayoutItem(); 1820 for (; pRootLayoutItem; 1821 pRootLayoutItem = 1822 (CXFA_ContainerLayoutItem*)pRootLayoutItem->m_pNextSibling) { 1823 CXFA_NodeIteratorTemplate< 1824 CXFA_ContainerLayoutItem, 1825 CXFA_TraverseStrategy_ContentAreaContainerLayoutItem> 1826 iterator(pRootLayoutItem); 1827 for (CXFA_ContainerLayoutItem* pContainerItem = iterator.GetCurrent(); 1828 pContainerItem; pContainerItem = iterator.MoveToNext()) { 1829 CXFA_Node* pNode = pContainerItem->m_pFormNode; 1830 switch (pNode->GetClassID()) { 1831 case XFA_ELEMENT_PageArea: 1832 m_pLayoutProcessor->GetRootRootItemLayoutProcessor() 1833 ->DoLayoutPageArea(pContainerItem); 1834 break; 1835 default: 1836 break; 1837 } 1838 } 1839 } 1840 } 1841 void XFA_SyncContainer(IXFA_Notify* pNotify, 1842 IXFA_DocLayout* pDocLayout, 1843 CXFA_LayoutItem* pContainerItem, 1844 FX_DWORD dwRelevant, 1845 FX_BOOL bVisible, 1846 int32_t nPageIndex) { 1847 FX_BOOL bVisibleItem = FALSE; 1848 FX_DWORD dwStatus = 0; 1849 FX_DWORD dwRelevantContainer = 0; 1850 if (bVisible) { 1851 XFA_ATTRIBUTEENUM eAttributeValue = 1852 pContainerItem->m_pFormNode->GetEnum(XFA_ATTRIBUTE_Presence); 1853 if (eAttributeValue == XFA_ATTRIBUTEENUM_Visible || 1854 eAttributeValue == XFA_ATTRIBUTEENUM_Unknown) { 1855 bVisibleItem = TRUE; 1856 } 1857 dwRelevantContainer = 1858 XFA_GetRelevant(pContainerItem->m_pFormNode, dwRelevant); 1859 dwStatus = 1860 (bVisibleItem ? XFA_LAYOUTSTATUS_Visible : 0) | dwRelevantContainer; 1861 } 1862 pNotify->OnLayoutEvent(pDocLayout, pContainerItem, XFA_LAYOUTEVENT_ItemAdded, 1863 (void*)(uintptr_t)nPageIndex, 1864 (void*)(uintptr_t)dwStatus); 1865 for (CXFA_LayoutItem* pChild = pContainerItem->m_pFirstChild; pChild; 1866 pChild = pChild->m_pNextSibling) { 1867 if (pChild->IsContentLayoutItem()) { 1868 XFA_SyncContainer(pNotify, pDocLayout, pChild, dwRelevantContainer, 1869 bVisibleItem, nPageIndex); 1870 } 1871 } 1872 } 1873 void CXFA_LayoutPageMgr::SyncLayoutData() { 1874 MergePageSetContents(); 1875 LayoutPageSetContents(); 1876 IXFA_Notify* pNotify = 1877 m_pTemplatePageSetRoot->GetDocument()->GetParser()->GetNotify(); 1878 int32_t nPageIdx = -1; 1879 CXFA_ContainerLayoutItem* pRootLayoutItem = this->GetRootLayoutItem(); 1880 for (; pRootLayoutItem; 1881 pRootLayoutItem = 1882 (CXFA_ContainerLayoutItem*)pRootLayoutItem->m_pNextSibling) { 1883 CXFA_NodeIteratorTemplate< 1884 CXFA_ContainerLayoutItem, 1885 CXFA_TraverseStrategy_ContentAreaContainerLayoutItem> 1886 iteratorParent(pRootLayoutItem); 1887 for (CXFA_ContainerLayoutItem* pContainerItem = iteratorParent.GetCurrent(); 1888 pContainerItem; pContainerItem = iteratorParent.MoveToNext()) { 1889 switch (pContainerItem->m_pFormNode->GetClassID()) { 1890 case XFA_ELEMENT_PageArea: { 1891 nPageIdx++; 1892 FX_DWORD dwRelevant = 1893 XFA_LAYOUTSTATUS_Viewable | XFA_LAYOUTSTATUS_Printable; 1894 CXFA_NodeIteratorTemplate<CXFA_LayoutItem, 1895 CXFA_TraverseStrategy_LayoutItem> 1896 iterator(pContainerItem); 1897 CXFA_LayoutItem* pChildLayoutItem = iterator.GetCurrent(); 1898 while (pChildLayoutItem) { 1899 CXFA_ContentLayoutItem* pContentItem = 1900 pChildLayoutItem->AsContentLayoutItem(); 1901 if (!pContentItem) { 1902 pChildLayoutItem = iterator.MoveToNext(); 1903 continue; 1904 } 1905 FX_BOOL bVisible = 1906 (pContentItem->m_pFormNode->GetEnum(XFA_ATTRIBUTE_Presence) == 1907 XFA_ATTRIBUTEENUM_Visible); 1908 FX_DWORD dwRelevantChild = 1909 XFA_GetRelevant(pContentItem->m_pFormNode, dwRelevant); 1910 XFA_SyncContainer(pNotify, m_pLayoutProcessor, pContentItem, 1911 dwRelevantChild, bVisible, nPageIdx); 1912 pChildLayoutItem = iterator.SkipChildrenAndMoveToNext(); 1913 } 1914 } break; 1915 default: 1916 break; 1917 } 1918 } 1919 } 1920 int32_t nPage = m_PageArray.GetSize(); 1921 for (int32_t i = nPage - 1; i >= m_nAvailPages; i--) { 1922 CXFA_ContainerLayoutItem* pPage = m_PageArray[i]; 1923 m_PageArray.RemoveAt(i); 1924 pNotify->OnPageEvent(pPage, XFA_PAGEEVENT_PageRemoved); 1925 delete pPage; 1926 } 1927 ClearRecordList(); 1928 } 1929 void XFA_ReleaseLayoutItem_NoPageArea(CXFA_LayoutItem* pLayoutItem) { 1930 CXFA_LayoutItem* pNext, * pNode = pLayoutItem->m_pFirstChild; 1931 while (pNode) { 1932 pNext = pNode->m_pNextSibling; 1933 pNode->m_pParent = NULL; 1934 XFA_ReleaseLayoutItem_NoPageArea(pNode); 1935 pNode = pNext; 1936 } 1937 if (pLayoutItem->m_pFormNode->GetClassID() != XFA_ELEMENT_PageArea) { 1938 delete pLayoutItem; 1939 } 1940 } 1941 void CXFA_LayoutPageMgr::PrepareLayout() { 1942 m_pPageSetCurRoot = NULL; 1943 m_ePageSetMode = XFA_ATTRIBUTEENUM_OrderedOccurrence; 1944 m_nAvailPages = 0; 1945 ClearRecordList(); 1946 if (!m_pPageSetLayoutItemRoot) { 1947 return; 1948 } 1949 CXFA_ContainerLayoutItem* pRootLayoutItem = m_pPageSetLayoutItemRoot; 1950 if (pRootLayoutItem && 1951 pRootLayoutItem->m_pFormNode->GetPacketID() == XFA_XDPPACKET_Form) { 1952 CXFA_Node* pPageSetFormNode = pRootLayoutItem->m_pFormNode; 1953 pRootLayoutItem->m_pFormNode->GetDocument()->m_pPendingPageSet.RemoveAll(); 1954 if (pPageSetFormNode->HasFlag(XFA_NODEFLAG_HasRemoved)) { 1955 XFA_ReleaseLayoutItem(pRootLayoutItem); 1956 m_pPageSetLayoutItemRoot = NULL; 1957 pRootLayoutItem = NULL; 1958 pPageSetFormNode = NULL; 1959 m_PageArray.RemoveAll(); 1960 } 1961 while (pPageSetFormNode) { 1962 CXFA_Node* pNextPageSet = 1963 pPageSetFormNode->GetNextSameClassSibling(XFA_ELEMENT_PageSet); 1964 pPageSetFormNode->GetNodeItem(XFA_NODEITEM_Parent) 1965 ->RemoveChild(pPageSetFormNode, FALSE); 1966 pRootLayoutItem->m_pFormNode->GetDocument()->m_pPendingPageSet.Add( 1967 pPageSetFormNode); 1968 pPageSetFormNode = pNextPageSet; 1969 } 1970 } 1971 #if defined(_XFA_LAYOUTITEM_MAPCACHE_) || defined(_XFA_LAYOUTITEM_ProcessCACHE_) 1972 pRootLayoutItem = m_pPageSetLayoutItemRoot; 1973 CXFA_ContainerLayoutItem* pNextLayout = NULL; 1974 for (; pRootLayoutItem; pRootLayoutItem = pNextLayout) { 1975 pNextLayout = (CXFA_ContainerLayoutItem*)pRootLayoutItem->m_pNextSibling; 1976 SaveLayoutItem(pRootLayoutItem); 1977 delete pRootLayoutItem; 1978 } 1979 m_pPageSetLayoutItemRoot = NULL; 1980 #else 1981 IXFA_Notify* pNotify = 1982 m_pLayoutProcessor->GetDocument()->GetParser()->GetNotify(); 1983 pRootLayoutItem = m_pPageSetLayoutItemRoot; 1984 for (; pRootLayoutItem; 1985 pRootLayoutItem = 1986 (CXFA_ContainerLayoutItem*)pRootLayoutItem->m_pNextSibling) { 1987 CXFA_NodeIteratorTemplate<CXFA_ContainerLayoutItem, 1988 CXFA_TraverseStrategy_PageAreaContainerLayoutItem> 1989 iterator(pRootLayoutItem); 1990 for (CXFA_ContainerLayoutItem* pContainerItem = iterator.GetCurrent(); 1991 pContainerItem; pContainerItem = iterator.MoveToNext()) { 1992 if (pContainerItem->m_pFormNode->GetClassID() != XFA_ELEMENT_PageArea) { 1993 continue; 1994 } 1995 CXFA_NodeIteratorTemplate<CXFA_LayoutItem, 1996 CXFA_TraverseStrategy_LayoutItem> 1997 iterator(pContainerItem); 1998 for (CXFA_LayoutItem* pLayoutItem = iterator.GetCurrent(); pLayoutItem; 1999 pLayoutItem = iterator.MoveToNext()) { 2000 if (!pLayoutItem->IsContentLayoutItem()) { 2001 continue; 2002 } 2003 pNotify->OnLayoutEvent(m_pLayoutProcessor, pLayoutItem, 2004 XFA_LAYOUTEVENT_ItemRemoving); 2005 } 2006 pNotify->OnPageEvent(pContainerItem, XFA_PAGEEVENT_PageRemoved); 2007 } 2008 } 2009 pRootLayoutItem = m_pPageSetLayoutItemRoot; 2010 CXFA_ContainerLayoutItem* pNextLayout = NULL; 2011 for (; pRootLayoutItem; pRootLayoutItem = pNextLayout) { 2012 pNextLayout = (CXFA_ContainerLayoutItem*)pRootLayoutItem->m_pNextSibling; 2013 XFA_ReleaseLayoutItem_NoPageArea(pRootLayoutItem); 2014 } 2015 m_pPageSetLayoutItemRoot = NULL; 2016 #endif 2017 } 2018