Home | History | Annotate | Download | only in parser
      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 #ifndef XFA_FXFA_PARSER_XFA_LAYOUT_ITEMLAYOUT_H_
      8 #define XFA_FXFA_PARSER_XFA_LAYOUT_ITEMLAYOUT_H_
      9 
     10 #include <float.h>
     11 
     12 #include <list>
     13 #include <map>
     14 #include <tuple>
     15 #include <vector>
     16 
     17 #include "core/fxcrt/fx_basic.h"
     18 #include "core/fxcrt/fx_coordinates.h"
     19 #include "xfa/fxfa/fxfa_basic.h"
     20 
     21 #define XFA_LAYOUT_INVALIDNODE ((CXFA_Node*)(intptr_t)-1)
     22 #define XFA_LAYOUT_FLOAT_PERCISION (0.0005f)
     23 
     24 class CXFA_ContainerLayoutItem;
     25 class CXFA_ContentLayoutItem;
     26 class CXFA_ItemLayoutProcessor;
     27 class CXFA_LayoutPageMgr;
     28 class CXFA_LayoutProcessor;
     29 class CXFA_Node;
     30 
     31 enum class XFA_ItemLayoutProcessorResult {
     32   Done,
     33   PageFullBreak,
     34   RowFullBreak,
     35   ManualBreak,
     36 };
     37 
     38 enum class XFA_ItemLayoutProcessorStages {
     39   None,
     40   BookendLeader,
     41   BreakBefore,
     42   Keep,
     43   Container,
     44   BreakAfter,
     45   BookendTrailer,
     46   Done,
     47 };
     48 
     49 class CXFA_LayoutContext {
     50  public:
     51   CXFA_LayoutContext()
     52       : m_prgSpecifiedColumnWidths(nullptr),
     53         m_fCurColumnWidth(0),
     54         m_bCurColumnWidthAvaiable(false),
     55         m_pOverflowProcessor(nullptr),
     56         m_pOverflowNode(nullptr) {}
     57   ~CXFA_LayoutContext() {}
     58 
     59   CFX_ArrayTemplate<FX_FLOAT>* m_prgSpecifiedColumnWidths;
     60   FX_FLOAT m_fCurColumnWidth;
     61   bool m_bCurColumnWidthAvaiable;
     62   CXFA_ItemLayoutProcessor* m_pOverflowProcessor;
     63   CXFA_Node* m_pOverflowNode;
     64 };
     65 
     66 bool XFA_ItemLayoutProcessor_IsTakingSpace(CXFA_Node* pNode);
     67 
     68 class CXFA_ItemLayoutProcessor {
     69  public:
     70   static bool IncrementRelayoutNode(CXFA_LayoutProcessor* pLayoutProcessor,
     71                                     CXFA_Node* pNode,
     72                                     CXFA_Node* pParentNode);
     73 
     74   CXFA_ItemLayoutProcessor(CXFA_Node* pNode, CXFA_LayoutPageMgr* pPageMgr);
     75   ~CXFA_ItemLayoutProcessor();
     76 
     77   XFA_ItemLayoutProcessorResult DoLayout(bool bUseBreakControl,
     78                                          FX_FLOAT fHeightLimit,
     79                                          FX_FLOAT fRealHeight,
     80                                          CXFA_LayoutContext* pContext);
     81   void DoLayoutPageArea(CXFA_ContainerLayoutItem* pPageAreaLayoutItem);
     82 
     83   CFX_SizeF GetCurrentComponentSize();
     84   CXFA_Node* GetFormNode() { return m_pFormNode; }
     85   bool HasLayoutItem() const { return !!m_pLayoutItem; }
     86   CXFA_ContentLayoutItem* ExtractLayoutItem();
     87   void SplitLayoutItem(FX_FLOAT fSplitPos);
     88 
     89   FX_FLOAT FindSplitPos(FX_FLOAT fProposedSplitPos);
     90 
     91   bool ProcessKeepForSplit(
     92       CXFA_ItemLayoutProcessor* pParentProcessor,
     93       CXFA_ItemLayoutProcessor* pChildProcessor,
     94       XFA_ItemLayoutProcessorResult eRetValue,
     95       CFX_ArrayTemplate<CXFA_ContentLayoutItem*>* rgCurLineLayoutItem,
     96       FX_FLOAT* fContentCurRowAvailWidth,
     97       FX_FLOAT* fContentCurRowHeight,
     98       FX_FLOAT* fContentCurRowY,
     99       bool* bAddedItemInRow,
    100       bool* bForceEndPage,
    101       XFA_ItemLayoutProcessorResult* result);
    102   void ProcessUnUseOverFlow(CXFA_Node* pLeaderNode,
    103                             CXFA_Node* pTrailerNode,
    104                             CXFA_ContentLayoutItem* pTrailerItem,
    105                             CXFA_Node* pFormNode);
    106   bool IsAddNewRowForTrailer(CXFA_ContentLayoutItem* pTrailerItem);
    107   bool JudgeLeaderOrTrailerForOccur(CXFA_Node* pFormNode);
    108 
    109   CXFA_ContentLayoutItem* CreateContentLayoutItem(CXFA_Node* pFormNode);
    110 
    111   CXFA_Node* m_pFormNode;
    112   CXFA_ContentLayoutItem* m_pLayoutItem;
    113   CXFA_Node* m_pCurChildNode;
    114   FX_FLOAT m_fUsedSize;
    115   CXFA_LayoutPageMgr* m_pPageMgr;
    116   std::list<CXFA_Node*> m_PendingNodes;
    117   bool m_bBreakPending;
    118   CFX_ArrayTemplate<FX_FLOAT> m_rgSpecifiedColumnWidths;
    119   std::vector<CXFA_ContentLayoutItem*> m_arrayKeepItems;
    120   FX_FLOAT m_fLastRowWidth;
    121   FX_FLOAT m_fLastRowY;
    122   bool m_bUseInheriated;
    123   XFA_ItemLayoutProcessorResult m_ePreProcessRs;
    124 
    125  private:
    126   void SetCurrentComponentPos(const CFX_PointF& pos);
    127   void SetCurrentComponentSize(const CFX_SizeF& size);
    128 
    129   void SplitLayoutItem(CXFA_ContentLayoutItem* pLayoutItem,
    130                        CXFA_ContentLayoutItem* pSecondParent,
    131                        FX_FLOAT fSplitPos);
    132   FX_FLOAT InsertKeepLayoutItems();
    133   bool CalculateRowChildPosition(
    134       CFX_ArrayTemplate<CXFA_ContentLayoutItem*> (&rgCurLineLayoutItems)[3],
    135       XFA_ATTRIBUTEENUM eFlowStrategy,
    136       bool bContainerHeightAutoSize,
    137       bool bContainerWidthAutoSize,
    138       FX_FLOAT* fContentCalculatedWidth,
    139       FX_FLOAT* fContentCalculatedHeight,
    140       FX_FLOAT* fContentCurRowY,
    141       FX_FLOAT fContentCurRowHeight,
    142       FX_FLOAT fContentWidthLimit,
    143       bool bRootForceTb);
    144   void ProcessUnUseBinds(CXFA_Node* pFormNode);
    145   bool JudgePutNextPage(CXFA_ContentLayoutItem* pParentLayoutItem,
    146                         FX_FLOAT fChildHeight,
    147                         std::vector<CXFA_ContentLayoutItem*>* pKeepItems);
    148 
    149   void DoLayoutPositionedContainer(CXFA_LayoutContext* pContext);
    150   void DoLayoutTableContainer(CXFA_Node* pLayoutNode);
    151   XFA_ItemLayoutProcessorResult DoLayoutFlowedContainer(
    152       bool bUseBreakControl,
    153       XFA_ATTRIBUTEENUM eFlowStrategy,
    154       FX_FLOAT fHeightLimit,
    155       FX_FLOAT fRealHeight,
    156       CXFA_LayoutContext* pContext,
    157       bool bRootForceTb);
    158   void DoLayoutField();
    159 
    160   void GotoNextContainerNode(CXFA_Node*& pCurActionNode,
    161                              XFA_ItemLayoutProcessorStages& nCurStage,
    162                              CXFA_Node* pParentContainer,
    163                              bool bUsePageBreak);
    164 
    165   bool ProcessKeepNodesForCheckNext(CXFA_Node*& pCurActionNode,
    166                                     XFA_ItemLayoutProcessorStages& nCurStage,
    167                                     CXFA_Node*& pNextContainer,
    168                                     bool& bLastKeepNode);
    169 
    170   bool ProcessKeepNodesForBreakBefore(CXFA_Node*& pCurActionNode,
    171                                       XFA_ItemLayoutProcessorStages& nCurStage,
    172                                       CXFA_Node* pContainerNode);
    173 
    174   CXFA_Node* GetSubformSetParent(CXFA_Node* pSubformSet);
    175 
    176   bool m_bKeepBreakFinish;
    177   bool m_bIsProcessKeep;
    178   CXFA_Node* m_pKeepHeadNode;
    179   CXFA_Node* m_pKeepTailNode;
    180   CXFA_ContentLayoutItem* m_pOldLayoutItem;
    181   CXFA_ItemLayoutProcessor* m_pCurChildPreprocessor;
    182   XFA_ItemLayoutProcessorStages m_nCurChildNodeStage;
    183   std::map<CXFA_Node*, int32_t> m_PendingNodesCount;
    184   FX_FLOAT m_fWidthLimite;
    185   bool m_bHasAvailHeight;
    186 };
    187 
    188 #endif  // XFA_FXFA_PARSER_XFA_LAYOUT_ITEMLAYOUT_H_
    189