C++程序  |  375行  |  10.62 KB

// Copyright 2014 PDFium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
 
// Original code copyright 2014 Foxit Software Inc. http://www.foxitsoftware.com

#ifndef CORE_SRC_REFLOW_REFLOWEDPAGE_H_
#define CORE_SRC_REFLOW_REFLOWEDPAGE_H_

#include "../../include/reflow/reflowengine.h"

#define GET_SIGNED(a) ( (a)>0 ? a/a : (a==0 ? 0 : -a/a) )
class CRF_Data;
class CRF_LineData;
class CRF_CharData;
class CRF_PathData;
class CRF_ImageData;
class CRF_Table;
class CRF_AttrOperation;
class CRF_OperationDate;
class CPDF_ReflowedPage;
class CPDF_Rect;
typedef CFX_SegmentedArray<CRF_Data*> CRF_DataPtrArray;
class CRF_CharState;
typedef CFX_SegmentedArray<CRF_CharState> CRF_CharStateArray;
#define SST_GE		1
#define SST_BLSE	2
#define SST_ILSE	3
#define SST_IE		4
class CPDF_LayoutProcessor_Reflow : public IPDF_LayoutProcessor
{
public:
    CPDF_LayoutProcessor_Reflow();
    ~CPDF_LayoutProcessor_Reflow();
    void Init(FX_FLOAT TopIndent, FX_FLOAT fWidth, FX_FLOAT fHeight, CPDF_ReflowedPage* pReflowedPage, int flags, FX_FLOAT lineSpace);

    LayoutStatus	StartProcess(IPDF_LayoutElement* pElement, IFX_Pause* pPause, const CFX_AffineMatrix* pPDFMatrix = NULL);
    LayoutStatus	Continue();
    int				GetPosition();
protected:
    void	FitPageMode();
    void	ProcessElement(IPDF_LayoutElement* pElement, FX_FLOAT reflowWidth);
    FX_FLOAT GetElmWidth(IPDF_LayoutElement* pElement);
    CFX_FloatRect GetElmBBox(IPDF_LayoutElement* pElement);
    void	ProcessTable(FX_FLOAT dx);
    void	ProcessObjs(IPDF_LayoutElement* pElement, FX_FLOAT reflowWidth);
    void	ProcessObject(CPDF_PageObject* pObj, FX_FLOAT reflowWidth, CFX_AffineMatrix objMatrix);
    void	ProcessTextObject(CPDF_TextObject *pObj, FX_FLOAT reflowWidth, CFX_AffineMatrix objMatrix);
    void	ProcessPathObject(CPDF_PathObject *pObj, FX_FLOAT reflowWidth);
    void	ProcessUnitaryObjs(CPDF_PageObjects *pObjs, FX_FLOAT reflowWidth, CFX_AffineMatrix objMatrix);
    FX_INT32 LogicPreObj(CPDF_TextObject* pObj);
    int ProcessInsertObject(CPDF_TextObject* pObj, CFX_AffineMatrix formMatrix);
    FX_WCHAR GetPreChar();
    FX_BOOL IsSameTextObject(CPDF_TextObject* pTextObj1, CPDF_TextObject* pTextObj2);
    int GetCharWidth(FX_DWORD charCode, CPDF_Font* pFont) const;
    FX_BOOL	IsCanBreakAfter(FX_DWORD unicode);
    FX_BOOL	IsCanBreakBefore(FX_DWORD unicode);
    FX_INT32 GetElementTypes(LayoutType layoutType);
    void				CreateRFData(CPDF_PageObject* pObj, CFX_AffineMatrix* pMatrix = NULL);
    CRF_CharState*		GetCharState(CPDF_TextObject* pObj, CPDF_Font* pFont, FX_FLOAT fHeight, FX_ARGB color);
    FX_FLOAT		ConverWidth(FX_FLOAT width);
    void	AddData2CurrLine(CRF_Data* pData);
    void	AddTemp2CurrLine(int begin, int count );
    void	Transform(const CFX_AffineMatrix* pMatrix, CRF_Data* pData);
    void	Transform(const CFX_AffineMatrix* pMatrix, CRF_DataPtrArray* pDataArray, int beginPos, int count = 0);
    FX_FLOAT GetDatasWidth( int beginPos, int endpos);
    void	UpdateCurrLine();
    FX_BOOL	FinishedCurrLine();
    int m_flags;
    CFX_AffineMatrix m_PDFMatrix;
    LayoutStatus	m_Status;
    CPDF_TextObject* m_pPreObj;
    CFX_AffineMatrix m_perMatrix;
    IPDF_LayoutElement*	m_pLayoutElement;
    IPDF_LayoutElement* m_pRootElement;
    FX_FLOAT		m_CurrRefWidth;
    IFX_Pause*		m_pPause;
    LayoutEnum		m_CurrWritingMode;
    CPDF_ReflowedPage*	m_pReflowedPage;
    FX_FLOAT		m_fRefWidth;
    FX_FLOAT		m_TopIndent;
    FX_FLOAT		m_fLineSpace;
    FX_FLOAT		m_fScreenHeight;
    FX_FLOAT		m_fCurrMaxWidth;
    FX_FLOAT		m_fCurrLineWidth;
    FX_FLOAT		m_fCurrLineHeight;
    CRF_DataPtrArray*	m_pCurrLine;
    CRF_DataPtrArray*	m_pTempLine;
    FX_BOOL			m_bIllustration;
    FX_FLOAT		m_fLineHeight;
    LayoutEnum		m_TextAlign;
    FX_FLOAT		m_StartIndent;
    CFX_ArrayTemplate<CRF_Table*> m_TableArray;
    int				m_PausePosition;
};
struct RF_TableCell {
    int			m_BeginPos;
    int			m_EndPos;
    FX_FLOAT m_MaxWidth;
    FX_FLOAT m_PosX;
    FX_FLOAT	m_PosY;
    FX_FLOAT	m_CellWidth;
    FX_FLOAT m_CellHeight;
    int			m_RowSpan;
    int			m_ColSpan;
    LayoutEnum	m_BlockAlign;
    LayoutEnum	m_InlineAlign;
};
typedef CFX_ArrayTemplate<RF_TableCell*> CRF_TableCellArray;
class CRF_Table 
{
public:
    CRF_Table()
    {
        m_TableWidth = 0;
        m_nCol = 0;
    }
    CRF_TableCellArray  m_pCellArray;
    CFX_WordArray		m_nCell;
    int					m_nCol;
    FX_FLOAT			m_TableWidth;
    FX_FLOAT			m_ReflowPageHeight;
};
class CRF_CharState 
{
public:
    CPDF_Font*	m_pFont;
    FX_ARGB		m_Color;
    FX_BOOL		m_bVert;
    FX_FLOAT m_fFontSize;
    FX_FLOAT m_fAscent;
    FX_FLOAT m_fDescent;

    CPDF_TextObject*	m_pTextObj;
};
class CRF_PageInfo 
{
public:
    CRF_PageInfo(CPDF_PageObject* pPageObj, CRF_PageInfo* pParent = NULL)
        : m_pPageObj(pPageObj) , m_pParent(pParent)
    {
    }
    CPDF_PageObject* GetPageObj()
    {
        return m_pPageObj;
    }
    CPDF_Dictionary* GetFormDict()
    {
        if (NULL == m_pParent) {
            return NULL;
        }
        CPDF_PageObject* pParentObj = m_pParent->GetPageObj();
        if (NULL == pParentObj || PDFPAGE_FORM != pParentObj->m_Type) {
            return NULL;
        }
        return ((CPDF_FormObject*)pParentObj)->m_pForm->m_pResources;
    }
protected:
    CPDF_PageObject*		m_pPageObj;
    CRF_PageInfo*			m_pParent;
};
class CPDF_ReflowedPage : public IPDF_ReflowedPage, public CFX_PrivateData
{
public:

    CPDF_ReflowedPage(CFX_GrowOnlyPool*	pMemoryPool);
    ~CPDF_ReflowedPage();
    CFX_PrivateData*	GetPrivateDataCtrl()
    {
        return this;
    };
    void		GetDisplayMatrix(CFX_AffineMatrix& matrix, FX_INT32 xPos, FX_INT32 yPos, FX_INT32 xSize, FX_INT32 ySize, FX_INT32 iRotate, const CFX_AffineMatrix* pPageMatrix);

    FX_FLOAT	GetPageHeight() ;
    FX_FLOAT	GetPageWidth()
    {
        return m_PageWidth;
    };
    void		FocusGetData(const CFX_AffineMatrix matrix, FX_INT32 x, FX_INT32 y, CFX_ByteString& str);
    FX_BOOL		FocusGetPosition(const CFX_AffineMatrix matrix, CFX_ByteString str, FX_INT32& x, FX_INT32& y);
    CRF_DataPtrArray*	m_pReflowed;
    FX_FLOAT			m_PageWidth;
    FX_FLOAT			m_PageHeight;
    FX_BOOL				m_bWaiting;
    CRF_CharStateArray*	m_pCharState;
    CFX_GrowOnlyPool*	m_pMemoryPool;
    FX_BOOL				m_bCreateMemoryPool;
    CPDF_Page*			m_pPDFPage;
    FX_BOOL					RetainPageObjsMemberShip();
    void					MarkPageObjMemberShip(CPDF_PageObject* pObj, CRF_PageInfo* pParent);
    void					ReleasePageObjsMemberShip();
    CPDF_Dictionary*		GetFormResDict(CPDF_PageObject* pObj);

    CFX_MapPtrToPtr*		m_pPageInfos;
};
class CPDF_ProgressiveReflowPageParser : public IPDF_ProgressiveReflowPageParser
{
public:
    CPDF_ProgressiveReflowPageParser();
    ~CPDF_ProgressiveReflowPageParser() ;
    void			Init();

    ParseStatus		GetStatus()
    {
        return m_Status;
    };

    void			SetParserStyle(RF_ParseStyle style)
    {
        m_ParseStyle = style;
    };
    void			Start(IPDF_ReflowedPage* pReflowPage, CPDF_Page* pPage, FX_FLOAT TopIndent, FX_FLOAT fWidth, FX_FLOAT fHeight, IFX_Pause* pPause, int flags);
    void			Continue(IFX_Pause* pPause);
    int				GetPosition() ;

    void			Clear();
    ParseStatus		m_Status;
protected:
    RF_ParseStyle		m_ParseStyle;
    CPDF_Page*			m_pPDFPage;
    IFX_Pause*			m_pPause;
    CPDF_ReflowedPage*	m_pReflowPage;
    FX_FLOAT			m_TopIndent;
    FX_FLOAT			m_ReflowedWidth;
    FX_FLOAT			m_fScreenHeight;
    IPDF_LayoutProvider*	m_pProvider;
    IPDF_LayoutProcessor*	m_pReflowEngine;
    int					m_nObjProcessed;
    int m_flags;
};
class CPDF_ProgressiveReflowPageRender : public IPDF_ProgressiveReflowPageRender
{
public:
    CPDF_ProgressiveReflowPageRender();
    ~CPDF_ProgressiveReflowPageRender() ;

    RenderStatus			GetStatus()
    {
        return m_Status;
    };


    void		SetDisplayColor(FX_COLORREF color);
    void		Start(IPDF_ReflowedPage* pReflowPage, CFX_RenderDevice* pDevice, const CFX_AffineMatrix* pMatrix, IFX_Pause* pPause, int DitherBits);
    void		Continue(IFX_Pause* pPause);
    int			GetPosition();


    void				Clear();
protected:
    void				Display(IFX_Pause* pPause);
    RenderStatus m_Status;
    CPDF_ReflowedPage*	m_pReflowPage;
    CFX_AffineMatrix*	m_pDisplayMatrix;
    int					m_CurrNum;
    IFX_FontEncoding*	m_pFontEncoding;
    CFX_RenderDevice*	m_pFXDevice;
    int					m_DitherBits;
    FX_COLORREF			m_DisplayColor;
    typedef struct CRF_TextDataAtt {
        CRF_TextDataAtt()
        {
            pFont = NULL;
            fFontSize = 0.0f;
            Color = 0;
        }
        CRF_TextDataAtt(CPDF_Font* font, FX_FLOAT fontSize, FX_ARGB color)
        {
            pFont = font;
            fFontSize = fontSize;
            Color = color;
        }
        CPDF_Font*  pFont;
        FX_FLOAT    fFontSize;
        FX_ARGB		Color;
    } CRF_TEXTDATAATT;
    inline bool isTextDataAttSame(CRF_TEXTDATAATT data1, CRF_TEXTDATAATT data2)
    {
        if (data1.pFont != data2.pFont) {
            return false;
        }
        if (data1.Color != data2.Color) {
            return false;
        }
        if (fabs(data1.fFontSize - data2.fFontSize) > 0.0f) {
            return false;
        }
        return true;
    };
};
#define TYPE_UNKNOW		0
#define TYPE_TEXT		1
#define TYPE_PATH		2
#define TYPE_IMAGE		3
#define TYPE_LINE		4
class CRF_Data 
{
public:
    typedef enum {Unknow, Text, Image, Path, Line, paragraph} RF_DataType;
    CRF_Data()
    {
        m_Type = Unknow;
        m_Width = 0;
        m_PosY = 0;
        m_PosX = 0;
        m_Height = 0;
    }
    RF_DataType	GetType()
    {
        return m_Type;
    }
    virtual		~CRF_Data() {}
    RF_DataType 	m_Type;
    FX_FLOAT	m_PosX;
    FX_FLOAT	m_PosY;
    FX_FLOAT	m_Width;
    FX_FLOAT	m_Height;
};
class CRF_LineData : public CRF_Data
{
public:
    CRF_LineData()
    {
        m_Type = Line;
    }
};
class CRF_CharData : public CRF_Data
{
public:
    CRF_CharData()
    {
        m_Type = Text;
        m_CharCode = -1;
    }
    CRF_CharState*	m_pCharState;
    FX_DWORD		m_CharCode;
};
class CRF_ImageData : public CRF_Data
{
public:
    CRF_ImageData()
    {
        m_Type = Image;
        m_pBitmap = NULL;
    }
    ~CRF_ImageData()
    {
        if(m_pBitmap) {
            delete m_pBitmap;
        }
        m_pBitmap = NULL;
    }
    CFX_AffineMatrix m_Matrix;
    CFX_DIBitmap*	m_pBitmap;
};
class CRF_PathData : public CRF_Data
{
public:
    CRF_PathData()
    {
        m_Type = Path;
        m_bDecoration = FALSE;
    }
    ~CRF_PathData() {};
    FX_BOOL			m_bDecoration;
    CPDF_Path			m_pPathData;
    CFX_AffineMatrix	m_pPath2Device;
    CPDF_GraphState		m_pGraphState;
    FX_ARGB		m_fill_argb;
    FX_ARGB		m_stroke_argb;
    int			m_fill_mode;
};

#endif  // CORE_SRC_REFLOW_REFLOWEDPAGE_H_