// 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 XFA_FDE_CFDE_RENDERDEVICE_H_
#define XFA_FDE_CFDE_RENDERDEVICE_H_

#include <vector>

#include "core/fxge/cfx_renderdevice.h"
#include "xfa/fgas/font/cfgas_gefont.h"

class CFDE_Brush;
class CFDE_Path;
class CFDE_Pen;
class CFX_GraphStateData;

class CFDE_RenderDevice {
 public:
  CFDE_RenderDevice(CFX_RenderDevice* pDevice, bool bOwnerDevice);
  ~CFDE_RenderDevice();

  int32_t GetWidth() const;
  int32_t GetHeight() const;
  void SaveState();
  void RestoreState();
  bool SetClipPath(const CFDE_Path* pClip);
  CFDE_Path* GetClipPath() const;
  bool SetClipRect(const CFX_RectF& rtClip);
  const CFX_RectF& GetClipRect();

  float GetDpiX() const;
  float GetDpiY() const;

  bool DrawImage(const CFX_RetainPtr<CFX_DIBSource>& pDib,
                 const CFX_RectF* pSrcRect,
                 const CFX_RectF& dstRect,
                 const CFX_Matrix* pImgMatrix = nullptr,
                 const CFX_Matrix* pDevMatrix = nullptr);
  bool DrawString(CFDE_Brush* pBrush,
                  const CFX_RetainPtr<CFGAS_GEFont>& pFont,
                  const FXTEXT_CHARPOS* pCharPos,
                  int32_t iCount,
                  float fFontSize,
                  const CFX_Matrix* pMatrix = nullptr);
  bool DrawBezier(CFDE_Pen* pPen,
                  float fPenWidth,
                  const CFX_PointF& pt1,
                  const CFX_PointF& pt2,
                  const CFX_PointF& pt3,
                  const CFX_PointF& pt4,
                  const CFX_Matrix* pMatrix = nullptr);
  bool DrawCurve(CFDE_Pen* pPen,
                 float fPenWidth,
                 const std::vector<CFX_PointF>& points,
                 bool bClosed,
                 float fTension = 0.5f,
                 const CFX_Matrix* pMatrix = nullptr);
  bool DrawEllipse(CFDE_Pen* pPen,
                   float fPenWidth,
                   const CFX_RectF& rect,
                   const CFX_Matrix* pMatrix = nullptr);
  bool DrawLines(CFDE_Pen* pPen,
                 float fPenWidth,
                 const std::vector<CFX_PointF>& points,
                 const CFX_Matrix* pMatrix = nullptr);
  bool DrawLine(CFDE_Pen* pPen,
                float fPenWidth,
                const CFX_PointF& pt1,
                const CFX_PointF& pt2,
                const CFX_Matrix* pMatrix = nullptr);
  bool DrawPath(CFDE_Pen* pPen,
                float fPenWidth,
                const CFDE_Path* pPath,
                const CFX_Matrix* pMatrix = nullptr);
  bool DrawPolygon(CFDE_Pen* pPen,
                   float fPenWidth,
                   const std::vector<CFX_PointF>& points,
                   const CFX_Matrix* pMatrix = nullptr);
  bool DrawRectangle(CFDE_Pen* pPen,
                     float fPenWidth,
                     const CFX_RectF& rect,
                     const CFX_Matrix* pMatrix = nullptr);
  bool FillClosedCurve(CFDE_Brush* pBrush,
                       const std::vector<CFX_PointF>& points,
                       float fTension = 0.5f,
                       const CFX_Matrix* pMatrix = nullptr);
  bool FillEllipse(CFDE_Brush* pBrush,
                   const CFX_RectF& rect,
                   const CFX_Matrix* pMatrix = nullptr);
  bool FillPath(CFDE_Brush* pBrush,
                const CFDE_Path* pPath,
                const CFX_Matrix* pMatrix = nullptr);
  bool FillPolygon(CFDE_Brush* pBrush,
                   const std::vector<CFX_PointF>& points,
                   const CFX_Matrix* pMatrix = nullptr);
  bool FillRectangle(CFDE_Brush* pBrush,
                     const CFX_RectF& rect,
                     const CFX_Matrix* pMatrix = nullptr);

  bool DrawSolidString(CFDE_Brush* pBrush,
                       const CFX_RetainPtr<CFGAS_GEFont>& pFont,
                       const FXTEXT_CHARPOS* pCharPos,
                       int32_t iCount,
                       float fFontSize,
                       const CFX_Matrix* pMatrix);
  bool DrawStringPath(CFDE_Brush* pBrush,
                      const CFX_RetainPtr<CFGAS_GEFont>& pFont,
                      const FXTEXT_CHARPOS* pCharPos,
                      int32_t iCount,
                      float fFontSize,
                      const CFX_Matrix* pMatrix);

 protected:
  bool CreatePen(CFDE_Pen* pPen,
                 float fPenWidth,
                 CFX_GraphStateData& graphState);

  CFX_RenderDevice* const m_pDevice;
  CFX_RectF m_rtClip;
  bool m_bOwnerDevice;
  int32_t m_iCharCount;
};

#endif  // XFA_FDE_CFDE_RENDERDEVICE_H_
