// 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_INCLUDE_FPDFAPI_FPDF_PAGE_H_
#define CORE_INCLUDE_FPDFAPI_FPDF_PAGE_H_

#include "core/include/fxge/fx_dib.h"
#include "fpdf_parser.h"
#include "fpdf_resource.h"

class CPDF_PageObjects;
class CPDF_Page;
class CPDF_Form;
class CPDF_ParseOptions;
class CPDF_PageObject;
class CPDF_PageRenderCache;
class CPDF_StreamFilter;
class CPDF_AllStates;
class CPDF_ContentParser;
class CPDF_StreamContentParser;
#define PDFTRANS_GROUP 0x0100
#define PDFTRANS_ISOLATED 0x0200
#define PDFTRANS_KNOCKOUT 0x0400

class CPDF_PageObjects {
 public:
  CPDF_PageObjects(FX_BOOL bReleaseMembers = TRUE);
  ~CPDF_PageObjects();

  void ContinueParse(IFX_Pause* pPause);

  FX_BOOL IsParsed() const { return m_ParseState == CONTENT_PARSED; }

  FX_POSITION GetFirstObjectPosition() const {
    return m_ObjectList.GetHeadPosition();
  }

  FX_POSITION GetLastObjectPosition() const {
    return m_ObjectList.GetTailPosition();
  }

  CPDF_PageObject* GetNextObject(FX_POSITION& pos) const {
    return (CPDF_PageObject*)m_ObjectList.GetNext(pos);
  }

  CPDF_PageObject* GetPrevObject(FX_POSITION& pos) const {
    return (CPDF_PageObject*)m_ObjectList.GetPrev(pos);
  }

  CPDF_PageObject* GetObjectAt(FX_POSITION pos) const {
    return (CPDF_PageObject*)m_ObjectList.GetAt(pos);
  }

  FX_DWORD CountObjects() const { return m_ObjectList.GetCount(); }

  int GetObjectIndex(CPDF_PageObject* pObj) const;

  CPDF_PageObject* GetObjectByIndex(int index) const;

  FX_POSITION InsertObject(FX_POSITION posInsertAfter,
                           CPDF_PageObject* pNewObject);

  void Transform(const CFX_Matrix& matrix);

  FX_BOOL BackgroundAlphaNeeded() const { return m_bBackgroundAlphaNeeded; }

  FX_BOOL HasImageMask() const { return m_bHasImageMask; }

  CFX_FloatRect CalcBoundingBox() const;

  CPDF_Dictionary* m_pFormDict;
  CPDF_Stream* m_pFormStream;
  CPDF_Document* m_pDocument;
  CPDF_Dictionary* m_pPageResources;
  CPDF_Dictionary* m_pResources;
  CFX_FloatRect m_BBox;
  int m_Transparency;

 protected:
  friend class CPDF_ContentParser;
  friend class CPDF_StreamContentParser;
  friend class CPDF_AllStates;

  enum ParseState { CONTENT_NOT_PARSED, CONTENT_PARSING, CONTENT_PARSED };

  void LoadTransInfo();
  void ClearCacheObjects();

  CFX_PtrList m_ObjectList;
  FX_BOOL m_bBackgroundAlphaNeeded;
  FX_BOOL m_bHasImageMask;
  FX_BOOL m_bReleaseMembers;
  CPDF_ContentParser* m_pParser;
  ParseState m_ParseState;
};

class CPDF_Page : public CPDF_PageObjects, public CFX_PrivateData {
 public:
  CPDF_Page();
  ~CPDF_Page();

  void Load(CPDF_Document* pDocument,
            CPDF_Dictionary* pPageDict,
            FX_BOOL bPageCache = TRUE);

  void StartParse(CPDF_ParseOptions* pOptions = NULL, FX_BOOL bReParse = FALSE);
  void ParseContent(CPDF_ParseOptions* pOptions = NULL,
                    FX_BOOL bReParse = FALSE);

  void GetDisplayMatrix(CFX_Matrix& matrix,
                        int xPos,
                        int yPos,
                        int xSize,
                        int ySize,
                        int iRotate) const;

  FX_FLOAT GetPageWidth() const { return m_PageWidth; }
  FX_FLOAT GetPageHeight() const { return m_PageHeight; }
  CFX_FloatRect GetPageBBox() const { return m_BBox; }
  const CFX_Matrix& GetPageMatrix() const { return m_PageMatrix; }
  CPDF_Object* GetPageAttr(const CFX_ByteStringC& name) const;
  CPDF_PageRenderCache* GetRenderCache() const { return m_pPageRender; }

 protected:
  friend class CPDF_ContentParser;
  FX_FLOAT m_PageWidth;
  FX_FLOAT m_PageHeight;
  CFX_Matrix m_PageMatrix;
  CPDF_PageRenderCache* m_pPageRender;
};
class CPDF_ParseOptions {
 public:
  CPDF_ParseOptions();

  FX_BOOL m_bTextOnly;

  FX_BOOL m_bMarkedContent;

  FX_BOOL m_bSeparateForm;

  FX_BOOL m_bDecodeInlineImage;
};
class CPDF_Form : public CPDF_PageObjects {
 public:
  CPDF_Form(CPDF_Document* pDocument,
            CPDF_Dictionary* pPageResources,
            CPDF_Stream* pFormStream,
            CPDF_Dictionary* pParentResources = NULL);

  ~CPDF_Form();

  void StartParse(CPDF_AllStates* pGraphicStates,
                  CFX_Matrix* pParentMatrix,
                  CPDF_Type3Char* pType3Char,
                  CPDF_ParseOptions* pOptions,
                  int level = 0);

  void ParseContent(CPDF_AllStates* pGraphicStates,
                    CFX_Matrix* pParentMatrix,
                    CPDF_Type3Char* pType3Char,
                    CPDF_ParseOptions* pOptions,
                    int level = 0);

  CPDF_Form* Clone() const;
};
class CPDF_PageContentGenerate {
 public:
  CPDF_PageContentGenerate(CPDF_Page* pPage);
  ~CPDF_PageContentGenerate();
  FX_BOOL InsertPageObject(CPDF_PageObject* pPageObject);
  void GenerateContent();
  void TransformContent(CFX_Matrix& matrix);

 protected:
  void ProcessImage(CFX_ByteTextBuf& buf, CPDF_ImageObject* pImageObj);
  void ProcessForm(CFX_ByteTextBuf& buf,
                   const uint8_t* data,
                   FX_DWORD size,
                   CFX_Matrix& matrix);
  CFX_ByteString RealizeResource(CPDF_Object* pResourceObj,
                                 const FX_CHAR* szType);

 private:
  CPDF_Page* m_pPage;
  CPDF_Document* m_pDocument;
  CFX_ArrayTemplate<CPDF_PageObject*> m_pageObjects;
};

#endif  // CORE_INCLUDE_FPDFAPI_FPDF_PAGE_H_
