// Copyright 2017 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

#include "fpdfsdk/cpdfsdk_appstream.h"

#include <math.h>

#include <iterator>
#include <memory>
#include <sstream>
#include <utility>

#include "constants/appearance.h"
#include "constants/form_flags.h"
#include "core/fpdfapi/font/cpdf_font.h"
#include "core/fpdfapi/parser/cpdf_dictionary.h"
#include "core/fpdfapi/parser/cpdf_document.h"
#include "core/fpdfapi/parser/cpdf_name.h"
#include "core/fpdfapi/parser/cpdf_number.h"
#include "core/fpdfapi/parser/cpdf_reference.h"
#include "core/fpdfapi/parser/cpdf_stream.h"
#include "core/fpdfapi/parser/cpdf_string.h"
#include "core/fpdfapi/parser/fpdf_parser_decode.h"
#include "core/fpdfapi/parser/fpdf_parser_utility.h"
#include "core/fpdfdoc/cpdf_bafontmap.h"
#include "core/fpdfdoc/cpdf_formcontrol.h"
#include "core/fpdfdoc/cpdf_icon.h"
#include "core/fpdfdoc/cpvt_word.h"
#include "core/fxcrt/fx_string_wrappers.h"
#include "fpdfsdk/cpdfsdk_formfillenvironment.h"
#include "fpdfsdk/cpdfsdk_interactiveform.h"
#include "fpdfsdk/cpdfsdk_pageview.h"
#include "fpdfsdk/cpdfsdk_widget.h"
#include "fpdfsdk/pwl/cpwl_edit.h"
#include "fpdfsdk/pwl/cpwl_edit_impl.h"
#include "fpdfsdk/pwl/cpwl_wnd.h"
#include "third_party/base/numerics/safe_conversions.h"
#include "third_party/base/span.h"

namespace {

// Checkbox & radiobutton styles.
enum class CheckStyle { kCheck = 0, kCircle, kCross, kDiamond, kSquare, kStar };

// Pushbutton layout styles.
enum class ButtonStyle {
  kLabel = 0,
  kIcon,
  kIconTopLabelBottom,
  kIconBottomLabelTop,
  kIconLeftLabelRight,
  kIconRightLabelLeft,
  kLabelOverIcon
};

const char kAppendRectOperator[] = "re";
const char kConcatMatrixOperator[] = "cm";
const char kCurveToOperator[] = "c";
const char kEndPathNoFillOrStrokeOperator[] = "n";
const char kFillOperator[] = "f";
const char kFillEvenOddOperator[] = "f*";
const char kInvokeNamedXObjectOperator[] = "Do";
const char kLineToOperator[] = "l";
const char kMarkedSequenceBeginOperator[] = "BMC";
const char kMarkedSequenceEndOperator[] = "EMC";
const char kMoveTextPositionOperator[] = "Td";
const char kMoveToOperator[] = "m";
const char kSetCMYKOperator[] = "k";
const char kSetCMKYStrokedOperator[] = "K";
const char kSetDashOperator[] = "d";
const char kSetGrayOperator[] = "g";
const char kSetGrayStrokedOperator[] = "G";
const char kSetLineCapStyleOperator[] = "J";
const char kSetLineJoinStyleOperator[] = "j";
const char kSetLineWidthOperator[] = "w";
const char kSetNonZeroWindingClipOperator[] = "W";
const char kSetRGBOperator[] = "rg";
const char kSetRGBStrokedOperator[] = "RG";
const char kSetTextFontAndSizeOperator[] = "Tf";
const char kShowTextOperator[] = "Tj";
const char kStateRestoreOperator[] = "Q";
const char kStateSaveOperator[] = "q";
const char kStrokeOperator[] = "S";
const char kTextBeginOperator[] = "BT";
const char kTextEndOperator[] = "ET";

class AutoClosedCommand {
 public:
  AutoClosedCommand(fxcrt::ostringstream* stream,
                    ByteString open,
                    ByteString close)
      : stream_(stream), close_(close) {
    *stream_ << open << "\n";
  }

  virtual ~AutoClosedCommand() { *stream_ << close_ << "\n"; }

 private:
  UnownedPtr<fxcrt::ostringstream> const stream_;
  ByteString close_;
};

class AutoClosedQCommand final : public AutoClosedCommand {
 public:
  explicit AutoClosedQCommand(fxcrt::ostringstream* stream)
      : AutoClosedCommand(stream, kStateSaveOperator, kStateRestoreOperator) {}
  ~AutoClosedQCommand() override = default;
};

void WriteMove(fxcrt::ostringstream& stream, const CFX_PointF& point) {
  stream << point.x << " " << point.y << " " << kMoveToOperator << "\n";
}

void WriteLine(fxcrt::ostringstream& stream, const CFX_PointF& point) {
  stream << point.x << " " << point.y << " " << kLineToOperator << "\n";
}

void WriteClosedLoop(fxcrt::ostringstream& stream,
                     pdfium::span<const CFX_PointF> points) {
  WriteMove(stream, points[0]);
  for (const auto& point : points.subspan(1))
    WriteLine(stream, point);
  WriteLine(stream, points[0]);
}

void WriteBezierCurve(fxcrt::ostringstream& stream,
                      const CFX_PointF& point1,
                      const CFX_PointF& point2,
                      const CFX_PointF& point3) {
  stream << point1.x << " " << point1.y << " " << point2.x << " " << point2.y
         << " " << point3.x << " " << point3.y << " " << kCurveToOperator
         << "\n";
}

void WriteAppendRect(fxcrt::ostringstream& stream, const CFX_FloatRect& rect) {
  stream << rect.left << " " << rect.bottom << " " << rect.Width() << " "
         << rect.Height() << " " << kAppendRectOperator << "\n";
}

ByteString GetStrokeColorAppStream(const CFX_Color& color) {
  fxcrt::ostringstream sColorStream;
  switch (color.nColorType) {
    case CFX_Color::Type::kTransparent:
      break;
    case CFX_Color::Type::kGray:
      sColorStream << color.fColor1 << " " << kSetGrayStrokedOperator << "\n";
      break;
    case CFX_Color::Type::kRGB:
      sColorStream << color.fColor1 << " " << color.fColor2 << " "
                   << color.fColor3 << " " << kSetRGBStrokedOperator << "\n";
      break;
    case CFX_Color::Type::kCMYK:
      sColorStream << color.fColor1 << " " << color.fColor2 << " "
                   << color.fColor3 << " " << color.fColor4 << " "
                   << kSetCMKYStrokedOperator << "\n";
      break;
  }
  return ByteString(sColorStream);
}

ByteString GetFillColorAppStream(const CFX_Color& color) {
  fxcrt::ostringstream sColorStream;
  switch (color.nColorType) {
    case CFX_Color::Type::kTransparent:
      break;
    case CFX_Color::Type::kGray:
      sColorStream << color.fColor1 << " " << kSetGrayOperator << "\n";
      break;
    case CFX_Color::Type::kRGB:
      sColorStream << color.fColor1 << " " << color.fColor2 << " "
                   << color.fColor3 << " " << kSetRGBOperator << "\n";
      break;
    case CFX_Color::Type::kCMYK:
      sColorStream << color.fColor1 << " " << color.fColor2 << " "
                   << color.fColor3 << " " << color.fColor4 << " "
                   << kSetCMYKOperator << "\n";
      break;
  }
  return ByteString(sColorStream);
}

ByteString GetAP_Check(const CFX_FloatRect& crBBox) {
  const float fWidth = crBBox.Width();
  const float fHeight = crBBox.Height();

  CFX_PointF pts[8][3] = {{CFX_PointF(0.28f, 0.52f), CFX_PointF(0.27f, 0.48f),
                           CFX_PointF(0.29f, 0.40f)},
                          {CFX_PointF(0.30f, 0.33f), CFX_PointF(0.31f, 0.29f),
                           CFX_PointF(0.31f, 0.28f)},
                          {CFX_PointF(0.39f, 0.28f), CFX_PointF(0.49f, 0.29f),
                           CFX_PointF(0.77f, 0.67f)},
                          {CFX_PointF(0.76f, 0.68f), CFX_PointF(0.78f, 0.69f),
                           CFX_PointF(0.76f, 0.75f)},
                          {CFX_PointF(0.76f, 0.75f), CFX_PointF(0.73f, 0.80f),
                           CFX_PointF(0.68f, 0.75f)},
                          {CFX_PointF(0.68f, 0.74f), CFX_PointF(0.68f, 0.74f),
                           CFX_PointF(0.44f, 0.47f)},
                          {CFX_PointF(0.43f, 0.47f), CFX_PointF(0.40f, 0.47f),
                           CFX_PointF(0.41f, 0.58f)},
                          {CFX_PointF(0.40f, 0.60f), CFX_PointF(0.28f, 0.66f),
                           CFX_PointF(0.30f, 0.56f)}};

  for (size_t i = 0; i < std::size(pts); ++i) {
    for (size_t j = 0; j < std::size(pts[0]); ++j) {
      pts[i][j].x = pts[i][j].x * fWidth + crBBox.left;
      pts[i][j].y *= pts[i][j].y * fHeight + crBBox.bottom;
    }
  }

  fxcrt::ostringstream csAP;
  WriteMove(csAP, pts[0][0]);

  for (size_t i = 0; i < std::size(pts); ++i) {
    size_t nNext = i < std::size(pts) - 1 ? i + 1 : 0;
    const CFX_PointF& pt_next = pts[nNext][0];

    float px1 = pts[i][1].x - pts[i][0].x;
    float py1 = pts[i][1].y - pts[i][0].y;
    float px2 = pts[i][2].x - pt_next.x;
    float py2 = pts[i][2].y - pt_next.y;

    WriteBezierCurve(
        csAP,
        {pts[i][0].x + px1 * FXSYS_BEZIER, pts[i][0].y + py1 * FXSYS_BEZIER},
        {pt_next.x + px2 * FXSYS_BEZIER, pt_next.y + py2 * FXSYS_BEZIER},
        pt_next);
  }

  return ByteString(csAP);
}

ByteString GetAP_Circle(const CFX_FloatRect& crBBox) {
  fxcrt::ostringstream csAP;

  float fWidth = crBBox.Width();
  float fHeight = crBBox.Height();

  CFX_PointF pt1(crBBox.left, crBBox.bottom + fHeight / 2);
  CFX_PointF pt2(crBBox.left + fWidth / 2, crBBox.top);
  CFX_PointF pt3(crBBox.right, crBBox.bottom + fHeight / 2);
  CFX_PointF pt4(crBBox.left + fWidth / 2, crBBox.bottom);

  WriteMove(csAP, pt1);

  float px = pt2.x - pt1.x;
  float py = pt2.y - pt1.y;

  WriteBezierCurve(csAP, {pt1.x, pt1.y + py * FXSYS_BEZIER},
                   {pt2.x - px * FXSYS_BEZIER, pt2.y}, pt2);

  px = pt3.x - pt2.x;
  py = pt2.y - pt3.y;

  WriteBezierCurve(csAP, {pt2.x + px * FXSYS_BEZIER, pt2.y},
                   {pt3.x, pt3.y + py * FXSYS_BEZIER}, pt3);

  px = pt3.x - pt4.x;
  py = pt3.y - pt4.y;

  WriteBezierCurve(csAP, {pt3.x, pt3.y - py * FXSYS_BEZIER},
                   {pt4.x + px * FXSYS_BEZIER, pt4.y}, pt4);

  px = pt4.x - pt1.x;
  py = pt1.y - pt4.y;

  WriteBezierCurve(csAP, {pt4.x - px * FXSYS_BEZIER, pt4.y},
                   {pt1.x, pt1.y - py * FXSYS_BEZIER}, pt1);

  return ByteString(csAP);
}

ByteString GetAP_Cross(const CFX_FloatRect& crBBox) {
  fxcrt::ostringstream csAP;

  WriteMove(csAP, {crBBox.left, crBBox.top});
  WriteLine(csAP, {crBBox.right, crBBox.bottom});
  WriteMove(csAP, {crBBox.left, crBBox.bottom});
  WriteLine(csAP, {crBBox.right, crBBox.top});

  return ByteString(csAP);
}

ByteString GetAP_Diamond(const CFX_FloatRect& crBBox) {
  fxcrt::ostringstream csAP;

  float fWidth = crBBox.Width();
  float fHeight = crBBox.Height();

  const CFX_PointF points[] = {{crBBox.left, crBBox.bottom + fHeight / 2},
                               {crBBox.left + fWidth / 2, crBBox.top},
                               {crBBox.right, crBBox.bottom + fHeight / 2},
                               {crBBox.left + fWidth / 2, crBBox.bottom}};
  WriteClosedLoop(csAP, points);

  return ByteString(csAP);
}

ByteString GetAP_Square(const CFX_FloatRect& crBBox) {
  fxcrt::ostringstream csAP;

  const CFX_PointF points[] = {{crBBox.left, crBBox.top},
                               {crBBox.right, crBBox.top},
                               {crBBox.right, crBBox.bottom},
                               {crBBox.left, crBBox.bottom}};
  WriteClosedLoop(csAP, points);

  return ByteString(csAP);
}

ByteString GetAP_Star(const CFX_FloatRect& crBBox) {
  fxcrt::ostringstream csAP;

  float fRadius = (crBBox.top - crBBox.bottom) / (1 + cosf(FXSYS_PI / 5.0f));
  CFX_PointF ptCenter = CFX_PointF((crBBox.left + crBBox.right) / 2.0f,
                                   (crBBox.top + crBBox.bottom) / 2.0f);

  CFX_PointF points[5];
  float fAngle = FXSYS_PI / 10.0f;
  for (auto& point : points) {
    point =
        ptCenter + CFX_PointF(fRadius * cosf(fAngle), fRadius * sinf(fAngle));
    fAngle += FXSYS_PI * 2 / 5.0f;
  }

  WriteMove(csAP, points[0]);

  int next = 0;
  for (size_t i = 0; i < std::size(points); ++i) {
    next = (next + 2) % std::size(points);
    WriteLine(csAP, points[next]);
  }

  return ByteString(csAP);
}

ByteString GetAP_HalfCircle(const CFX_FloatRect& crBBox, float fRotate) {
  fxcrt::ostringstream csAP;

  float fWidth = crBBox.Width();
  float fHeight = crBBox.Height();

  CFX_PointF pt1(-fWidth / 2, 0);
  CFX_PointF pt2(0, fHeight / 2);
  CFX_PointF pt3(fWidth / 2, 0);

  float px;
  float py;

  csAP << cos(fRotate) << " " << sin(fRotate) << " " << -sin(fRotate) << " "
       << cos(fRotate) << " " << crBBox.left + fWidth / 2 << " "
       << crBBox.bottom + fHeight / 2 << " " << kConcatMatrixOperator << "\n";

  WriteMove(csAP, pt1);

  px = pt2.x - pt1.x;
  py = pt2.y - pt1.y;

  WriteBezierCurve(csAP, {pt1.x, pt1.y + py * FXSYS_BEZIER},
                   {pt2.x - px * FXSYS_BEZIER, pt2.y}, pt2);

  px = pt3.x - pt2.x;
  py = pt2.y - pt3.y;

  WriteBezierCurve(csAP, {pt2.x + px * FXSYS_BEZIER, pt2.y},
                   {pt3.x, pt3.y + py * FXSYS_BEZIER}, pt3);

  return ByteString(csAP);
}

ByteString GetAppStream_Check(const CFX_FloatRect& rcBBox,
                              const CFX_Color& crText) {
  fxcrt::ostringstream sAP;
  {
    AutoClosedQCommand q(&sAP);
    sAP << GetFillColorAppStream(crText) << GetAP_Check(rcBBox) << kFillOperator
        << "\n";
  }
  return ByteString(sAP);
}

ByteString GetAppStream_Circle(const CFX_FloatRect& rcBBox,
                               const CFX_Color& crText) {
  fxcrt::ostringstream sAP;
  {
    AutoClosedQCommand q(&sAP);
    sAP << GetFillColorAppStream(crText) << GetAP_Circle(rcBBox)
        << kFillOperator << "\n";
  }
  return ByteString(sAP);
}

ByteString GetAppStream_Cross(const CFX_FloatRect& rcBBox,
                              const CFX_Color& crText) {
  fxcrt::ostringstream sAP;
  {
    AutoClosedQCommand q(&sAP);
    sAP << GetStrokeColorAppStream(crText) << GetAP_Cross(rcBBox)
        << kStrokeOperator << "\n";
  }
  return ByteString(sAP);
}

ByteString GetAppStream_Diamond(const CFX_FloatRect& rcBBox,
                                const CFX_Color& crText) {
  fxcrt::ostringstream sAP;
  {
    AutoClosedQCommand q(&sAP);
    sAP << "1 " << kSetLineWidthOperator << "\n"
        << GetFillColorAppStream(crText) << GetAP_Diamond(rcBBox)
        << kFillOperator << "\n";
  }
  return ByteString(sAP);
}

ByteString GetAppStream_Square(const CFX_FloatRect& rcBBox,
                               const CFX_Color& crText) {
  fxcrt::ostringstream sAP;
  {
    AutoClosedQCommand q(&sAP);
    sAP << GetFillColorAppStream(crText) << GetAP_Square(rcBBox)
        << kFillOperator << "\n";
  }
  return ByteString(sAP);
}

ByteString GetAppStream_Star(const CFX_FloatRect& rcBBox,
                             const CFX_Color& crText) {
  fxcrt::ostringstream sAP;
  {
    AutoClosedQCommand q(&sAP);
    sAP << GetFillColorAppStream(crText) << GetAP_Star(rcBBox) << kFillOperator
        << "\n";
  }
  return ByteString(sAP);
}

ByteString GetCircleFillAppStream(const CFX_FloatRect& rect,
                                  const CFX_Color& color) {
  fxcrt::ostringstream sAppStream;
  ByteString sColor = GetFillColorAppStream(color);
  if (sColor.GetLength() > 0) {
    AutoClosedQCommand q(&sAppStream);
    sAppStream << sColor << GetAP_Circle(rect) << kFillOperator << "\n";
  }
  return ByteString(sAppStream);
}

ByteString GetCircleBorderAppStream(const CFX_FloatRect& rect,
                                    float fWidth,
                                    const CFX_Color& color,
                                    const CFX_Color& crLeftTop,
                                    const CFX_Color& crRightBottom,
                                    BorderStyle nStyle,
                                    const CPWL_Dash& dash) {
  fxcrt::ostringstream sAppStream;
  ByteString sColor;

  if (fWidth > 0.0f) {
    AutoClosedQCommand q(&sAppStream);

    float fHalfWidth = fWidth / 2.0f;
    CFX_FloatRect rect_by_2 = rect.GetDeflated(fHalfWidth, fHalfWidth);

    float div = fHalfWidth * 0.75f;
    CFX_FloatRect rect_by_75 = rect.GetDeflated(div, div);
    switch (nStyle) {
      default:
      case BorderStyle::kSolid:
      case BorderStyle::kUnderline: {
        sColor = GetStrokeColorAppStream(color);
        if (sColor.GetLength() > 0) {
          AutoClosedQCommand q2(&sAppStream);
          sAppStream << fWidth << " " << kSetLineWidthOperator << "\n"
                     << sColor << GetAP_Circle(rect_by_2) << " "
                     << kStrokeOperator << "\n";
        }
      } break;
      case BorderStyle::kDash: {
        sColor = GetStrokeColorAppStream(color);
        if (sColor.GetLength() > 0) {
          AutoClosedQCommand q2(&sAppStream);
          sAppStream << fWidth << " " << kSetLineWidthOperator << "\n"
                     << "[" << dash.nDash << " " << dash.nGap << "] "
                     << dash.nPhase << " " << kSetDashOperator << "\n"
                     << sColor << GetAP_Circle(rect_by_2) << " "
                     << kStrokeOperator << "\n";
        }
      } break;
      case BorderStyle::kBeveled: {
        sColor = GetStrokeColorAppStream(color);
        if (sColor.GetLength() > 0) {
          AutoClosedQCommand q2(&sAppStream);
          sAppStream << fHalfWidth << " " << kSetLineWidthOperator << "\n"
                     << sColor << GetAP_Circle(rect) << " " << kStrokeOperator
                     << "\n";
        }
        sColor = GetStrokeColorAppStream(crLeftTop);
        if (sColor.GetLength() > 0) {
          AutoClosedQCommand q2(&sAppStream);
          sAppStream << fHalfWidth << " " << kSetLineWidthOperator << "\n"
                     << sColor << GetAP_HalfCircle(rect_by_75, FXSYS_PI / 4.0f)
                     << " " << kStrokeOperator << "\n";
        }
        sColor = GetStrokeColorAppStream(crRightBottom);
        if (sColor.GetLength() > 0) {
          AutoClosedQCommand q2(&sAppStream);
          sAppStream << fHalfWidth << " " << kSetLineWidthOperator << "\n"
                     << sColor
                     << GetAP_HalfCircle(rect_by_75, FXSYS_PI * 5 / 4.0f) << " "
                     << kStrokeOperator << "\n";
        }
      } break;
      case BorderStyle::kInset: {
        sColor = GetStrokeColorAppStream(color);
        if (sColor.GetLength() > 0) {
          AutoClosedQCommand q2(&sAppStream);
          sAppStream << fHalfWidth << " " << kSetLineWidthOperator << "\n"
                     << sColor << GetAP_Circle(rect) << " " << kStrokeOperator
                     << "\n";
        }
        sColor = GetStrokeColorAppStream(crLeftTop);
        if (sColor.GetLength() > 0) {
          AutoClosedQCommand q2(&sAppStream);
          sAppStream << fHalfWidth << " " << kSetLineWidthOperator << "\n"
                     << sColor << GetAP_HalfCircle(rect_by_75, FXSYS_PI / 4.0f)
                     << " " << kStrokeOperator << "\n";
        }
        sColor = GetStrokeColorAppStream(crRightBottom);
        if (sColor.GetLength() > 0) {
          AutoClosedQCommand q2(&sAppStream);
          sAppStream << fHalfWidth << " " << kSetLineWidthOperator << "\n"
                     << sColor
                     << GetAP_HalfCircle(rect_by_75, FXSYS_PI * 5 / 4.0f) << " "
                     << kStrokeOperator << "\n";
        }
      } break;
    }
  }
  return ByteString(sAppStream);
}

ByteString GetCheckBoxAppStream(const CFX_FloatRect& rcBBox,
                                CheckStyle nStyle,
                                const CFX_Color& crText) {
  CFX_FloatRect rcCenter = rcBBox.GetCenterSquare();
  switch (nStyle) {
    default:
    case CheckStyle::kCheck:
      return GetAppStream_Check(rcCenter, crText);
    case CheckStyle::kCircle:
      rcCenter.ScaleFromCenterPoint(2.0f / 3.0f);
      return GetAppStream_Circle(rcCenter, crText);
    case CheckStyle::kCross:
      return GetAppStream_Cross(rcCenter, crText);
    case CheckStyle::kDiamond:
      rcCenter.ScaleFromCenterPoint(2.0f / 3.0f);
      return GetAppStream_Diamond(rcCenter, crText);
    case CheckStyle::kSquare:
      rcCenter.ScaleFromCenterPoint(2.0f / 3.0f);
      return GetAppStream_Square(rcCenter, crText);
    case CheckStyle::kStar:
      rcCenter.ScaleFromCenterPoint(2.0f / 3.0f);
      return GetAppStream_Star(rcCenter, crText);
  }
}

ByteString GetRadioButtonAppStream(const CFX_FloatRect& rcBBox,
                                   CheckStyle nStyle,
                                   const CFX_Color& crText) {
  CFX_FloatRect rcCenter = rcBBox.GetCenterSquare();
  switch (nStyle) {
    default:
    case CheckStyle::kCheck:
      return GetAppStream_Check(rcCenter, crText);
    case CheckStyle::kCircle:
      rcCenter.ScaleFromCenterPoint(1.0f / 2.0f);
      return GetAppStream_Circle(rcCenter, crText);
    case CheckStyle::kCross:
      return GetAppStream_Cross(rcCenter, crText);
    case CheckStyle::kDiamond:
      rcCenter.ScaleFromCenterPoint(2.0f / 3.0f);
      return GetAppStream_Diamond(rcCenter, crText);
    case CheckStyle::kSquare:
      rcCenter.ScaleFromCenterPoint(2.0f / 3.0f);
      return GetAppStream_Square(rcCenter, crText);
    case CheckStyle::kStar:
      rcCenter.ScaleFromCenterPoint(2.0f / 3.0f);
      return GetAppStream_Star(rcCenter, crText);
  }
}

ByteString GetFontSetString(IPVT_FontMap* pFontMap,
                            int32_t nFontIndex,
                            float fFontSize) {
  if (!pFontMap)
    return ByteString();

  ByteString sFontAlias = pFontMap->GetPDFFontAlias(nFontIndex);
  if (sFontAlias.GetLength() <= 0 || fFontSize <= 0)
    return ByteString();

  fxcrt::ostringstream sRet;
  sRet << "/" << sFontAlias << " " << fFontSize << " "
       << kSetTextFontAndSizeOperator << "\n";
  return ByteString(sRet);
}

ByteString GetWordRenderString(ByteStringView strWords) {
  if (strWords.IsEmpty())
    return ByteString();
  return PDF_EncodeString(strWords) + " " + kShowTextOperator + "\n";
}

ByteString GetEditAppStream(CPWL_EditImpl* pEdit,
                            const CFX_PointF& ptOffset,
                            bool bContinuous,
                            uint16_t SubWord) {
  CPWL_EditImpl::Iterator* pIterator = pEdit->GetIterator();
  pIterator->SetAt(0);

  fxcrt::ostringstream sEditStream;
  int32_t nCurFontIndex = -1;
  CFX_PointF ptOld;
  CFX_PointF ptNew;
  CPVT_WordPlace oldplace;
  ByteString sWords;

  while (pIterator->NextWord()) {
    CPVT_WordPlace place = pIterator->GetAt();
    if (bContinuous) {
      if (place.LineCmp(oldplace) != 0) {
        if (!sWords.IsEmpty()) {
          sEditStream << GetWordRenderString(sWords.AsStringView());
          sWords.clear();
        }

        CPVT_Word word;
        if (pIterator->GetWord(word)) {
          ptNew = CFX_PointF(word.ptWord.x + ptOffset.x,
                             word.ptWord.y + ptOffset.y);
        } else {
          CPVT_Line line;
          pIterator->GetLine(line);
          ptNew = CFX_PointF(line.ptLine.x + ptOffset.x,
                             line.ptLine.y + ptOffset.y);
        }

        if (ptNew.x != ptOld.x || ptNew.y != ptOld.y) {
          sEditStream << ptNew.x - ptOld.x << " " << ptNew.y - ptOld.y << " "
                      << kMoveTextPositionOperator << "\n";

          ptOld = ptNew;
        }
      }

      CPVT_Word word;
      if (pIterator->GetWord(word)) {
        if (word.nFontIndex != nCurFontIndex) {
          if (!sWords.IsEmpty()) {
            sEditStream << GetWordRenderString(sWords.AsStringView());
            sWords.clear();
          }
          sEditStream << GetFontSetString(pEdit->GetFontMap(), word.nFontIndex,
                                          word.fFontSize);
          nCurFontIndex = word.nFontIndex;
        }

        sWords += pEdit->GetPDFWordString(nCurFontIndex, word.Word, SubWord);
      }
      oldplace = place;
    } else {
      CPVT_Word word;
      if (pIterator->GetWord(word)) {
        ptNew =
            CFX_PointF(word.ptWord.x + ptOffset.x, word.ptWord.y + ptOffset.y);

        if (ptNew.x != ptOld.x || ptNew.y != ptOld.y) {
          sEditStream << ptNew.x - ptOld.x << " " << ptNew.y - ptOld.y << " "
                      << kMoveTextPositionOperator << "\n";
          ptOld = ptNew;
        }
        if (word.nFontIndex != nCurFontIndex) {
          sEditStream << GetFontSetString(pEdit->GetFontMap(), word.nFontIndex,
                                          word.fFontSize);
          nCurFontIndex = word.nFontIndex;
        }
        sEditStream << GetWordRenderString(
            pEdit->GetPDFWordString(nCurFontIndex, word.Word, SubWord)
                .AsStringView());
      }
    }
  }

  if (!sWords.IsEmpty())
    sEditStream << GetWordRenderString(sWords.AsStringView());

  fxcrt::ostringstream sAppStream;
  if (sEditStream.tellp() > 0) {
    sAppStream << sEditStream.str();
  }
  return ByteString(sAppStream);
}

ByteString GenerateIconAppStream(CPDF_IconFit& fit,
                                 CPDF_Stream* pIconStream,
                                 const CFX_FloatRect& rcIcon) {
  if (rcIcon.IsEmpty() || !pIconStream)
    return ByteString();

  CPWL_Wnd::CreateParams cp(nullptr, nullptr, nullptr);
  cp.dwFlags = PWS_VISIBLE;
  auto pWnd = std::make_unique<CPWL_Wnd>(cp, nullptr);
  pWnd->Realize();
  if (!pWnd->Move(rcIcon, false, false))
    return ByteString();

  auto pPDFIcon = std::make_unique<CPDF_Icon>(pIconStream);
  ByteString sAlias = pPDFIcon->GetImageAlias();
  if (sAlias.GetLength() <= 0)
    return ByteString();

  const CFX_FloatRect rcPlate = pWnd->GetClientRect();
  const CFX_SizeF image_size = pPDFIcon->GetImageSize();
  const CFX_Matrix mt = pPDFIcon->GetImageMatrix().GetInverse();
  const CFX_VectorF scale = fit.GetScale(image_size, rcPlate);
  const CFX_VectorF offset = fit.GetImageOffset(image_size, scale, rcPlate);

  fxcrt::ostringstream str;
  {
    AutoClosedQCommand q(&str);
    WriteAppendRect(str, rcPlate);
    str << kSetNonZeroWindingClipOperator << " "
        << kEndPathNoFillOrStrokeOperator << "\n";

    str << scale.x << " 0 0 " << scale.y << " " << rcPlate.left + offset.x
        << " " << rcPlate.bottom + offset.y << " " << kConcatMatrixOperator
        << "\n";
    str << mt.a << " " << mt.b << " " << mt.c << " " << mt.d << " " << mt.e
        << " " << mt.f << " " << kConcatMatrixOperator << "\n";

    str << "0 " << kSetGrayOperator << " 0 " << kSetGrayStrokedOperator << " 1 "
        << kSetLineWidthOperator << " /" << sAlias << " "
        << kInvokeNamedXObjectOperator << "\n";
  }
  pWnd->Destroy();
  return ByteString(str);
}

ByteString GetPushButtonAppStream(const CFX_FloatRect& rcBBox,
                                  IPVT_FontMap* pFontMap,
                                  CPDF_Stream* pIconStream,
                                  CPDF_IconFit& IconFit,
                                  const WideString& sLabel,
                                  const CFX_Color& crText,
                                  float fFontSize,
                                  ButtonStyle nLayOut) {
  const float fAutoFontScale = 1.0f / 3.0f;

  auto pEdit = std::make_unique<CPWL_EditImpl>();
  pEdit->SetFontMap(pFontMap);
  pEdit->SetAlignmentH(1);
  pEdit->SetAlignmentV(1);
  pEdit->SetMultiLine(false);
  pEdit->SetAutoReturn(false);
  if (FXSYS_IsFloatZero(fFontSize))
    pEdit->SetAutoFontSize(true);
  else
    pEdit->SetFontSize(fFontSize);

  pEdit->Initialize();
  pEdit->SetText(sLabel);
  pEdit->Paint();

  CFX_FloatRect rcLabelContent = pEdit->GetContentRect();
  CFX_FloatRect rcLabel;
  CFX_FloatRect rcIcon;
  float fWidth = 0.0f;
  float fHeight = 0.0f;

  switch (nLayOut) {
    case ButtonStyle::kLabel:
      rcLabel = rcBBox;
      break;
    case ButtonStyle::kIcon:
      rcIcon = rcBBox;
      break;
    case ButtonStyle::kIconTopLabelBottom:
      if (pIconStream) {
        if (FXSYS_IsFloatZero(fFontSize)) {
          fHeight = rcBBox.Height();
          rcLabel = CFX_FloatRect(rcBBox.left, rcBBox.bottom, rcBBox.right,
                                  rcBBox.bottom + fHeight * fAutoFontScale);
          rcIcon =
              CFX_FloatRect(rcBBox.left, rcLabel.top, rcBBox.right, rcBBox.top);
        } else {
          fHeight = rcLabelContent.Height();

          if (rcBBox.bottom + fHeight > rcBBox.top) {
            rcLabel = rcBBox;
          } else {
            rcLabel = CFX_FloatRect(rcBBox.left, rcBBox.bottom, rcBBox.right,
                                    rcBBox.bottom + fHeight);
            rcIcon = CFX_FloatRect(rcBBox.left, rcLabel.top, rcBBox.right,
                                   rcBBox.top);
          }
        }
      } else {
        rcLabel = rcBBox;
      }
      break;
    case ButtonStyle::kIconBottomLabelTop:
      if (pIconStream) {
        if (FXSYS_IsFloatZero(fFontSize)) {
          fHeight = rcBBox.Height();
          rcLabel =
              CFX_FloatRect(rcBBox.left, rcBBox.top - fHeight * fAutoFontScale,
                            rcBBox.right, rcBBox.top);
          rcIcon = CFX_FloatRect(rcBBox.left, rcBBox.bottom, rcBBox.right,
                                 rcLabel.bottom);
        } else {
          fHeight = rcLabelContent.Height();

          if (rcBBox.bottom + fHeight > rcBBox.top) {
            rcLabel = rcBBox;
          } else {
            rcLabel = CFX_FloatRect(rcBBox.left, rcBBox.top - fHeight,
                                    rcBBox.right, rcBBox.top);
            rcIcon = CFX_FloatRect(rcBBox.left, rcBBox.bottom, rcBBox.right,
                                   rcLabel.bottom);
          }
        }
      } else {
        rcLabel = rcBBox;
      }
      break;
    case ButtonStyle::kIconLeftLabelRight:
      if (pIconStream) {
        if (FXSYS_IsFloatZero(fFontSize)) {
          fWidth = rcBBox.right - rcBBox.left;
          if (rcLabelContent.Width() < fWidth * fAutoFontScale) {
            rcLabel = CFX_FloatRect(rcBBox.right - fWidth * fAutoFontScale,
                                    rcBBox.bottom, rcBBox.right, rcBBox.top);
            rcIcon = CFX_FloatRect(rcBBox.left, rcBBox.bottom, rcLabel.left,
                                   rcBBox.top);
          } else {
            if (rcLabelContent.Width() < fWidth) {
              rcLabel = CFX_FloatRect(rcBBox.right - rcLabelContent.Width(),
                                      rcBBox.bottom, rcBBox.right, rcBBox.top);
              rcIcon = CFX_FloatRect(rcBBox.left, rcBBox.bottom, rcLabel.left,
                                     rcBBox.top);
            } else {
              rcLabel = rcBBox;
            }
          }
        } else {
          fWidth = rcLabelContent.Width();
          if (rcBBox.left + fWidth > rcBBox.right) {
            rcLabel = rcBBox;
          } else {
            rcLabel = CFX_FloatRect(rcBBox.right - fWidth, rcBBox.bottom,
                                    rcBBox.right, rcBBox.top);
            rcIcon = CFX_FloatRect(rcBBox.left, rcBBox.bottom, rcLabel.left,
                                   rcBBox.top);
          }
        }
      } else {
        rcLabel = rcBBox;
      }
      break;
    case ButtonStyle::kIconRightLabelLeft:
      if (pIconStream) {
        if (FXSYS_IsFloatZero(fFontSize)) {
          fWidth = rcBBox.right - rcBBox.left;
          if (rcLabelContent.Width() < fWidth * fAutoFontScale) {
            rcLabel = CFX_FloatRect(rcBBox.left, rcBBox.bottom,
                                    rcBBox.left + fWidth * fAutoFontScale,
                                    rcBBox.top);
            rcIcon = CFX_FloatRect(rcLabel.right, rcBBox.bottom, rcBBox.right,
                                   rcBBox.top);
          } else {
            if (rcLabelContent.Width() < fWidth) {
              rcLabel = CFX_FloatRect(rcBBox.left, rcBBox.bottom,
                                      rcBBox.left + rcLabelContent.Width(),
                                      rcBBox.top);
              rcIcon = CFX_FloatRect(rcLabel.right, rcBBox.bottom, rcBBox.right,
                                     rcBBox.top);
            } else {
              rcLabel = rcBBox;
            }
          }
        } else {
          fWidth = rcLabelContent.Width();
          if (rcBBox.left + fWidth > rcBBox.right) {
            rcLabel = rcBBox;
          } else {
            rcLabel = CFX_FloatRect(rcBBox.left, rcBBox.bottom,
                                    rcBBox.left + fWidth, rcBBox.top);
            rcIcon = CFX_FloatRect(rcLabel.right, rcBBox.bottom, rcBBox.right,
                                   rcBBox.top);
          }
        }
      } else {
        rcLabel = rcBBox;
      }
      break;
    case ButtonStyle::kLabelOverIcon:
      rcLabel = rcBBox;
      rcIcon = rcBBox;
      break;
  }

  fxcrt::ostringstream sTemp;
  sTemp << GenerateIconAppStream(IconFit, pIconStream, rcIcon);

  if (!rcLabel.IsEmpty()) {
    pEdit->SetPlateRect(rcLabel);
    pEdit->Paint();
    ByteString sEdit =
        GetEditAppStream(pEdit.get(), CFX_PointF(0.0f, 0.0f), true, 0);
    if (sEdit.GetLength() > 0) {
      AutoClosedCommand bt(&sTemp, kTextBeginOperator, kTextEndOperator);
      sTemp << GetFillColorAppStream(crText) << sEdit;
    }
  }

  if (sTemp.tellp() <= 0)
    return ByteString();

  fxcrt::ostringstream sAppStream;
  {
    AutoClosedQCommand q(&sAppStream);
    WriteAppendRect(sAppStream, rcBBox);
    sAppStream << kSetNonZeroWindingClipOperator << " "
               << kEndPathNoFillOrStrokeOperator << "\n";
    sAppStream << sTemp.str().c_str();
  }
  return ByteString(sAppStream);
}

ByteString GetBorderAppStreamInternal(const CFX_FloatRect& rect,
                                      float fWidth,
                                      const CFX_Color& color,
                                      const CFX_Color& crLeftTop,
                                      const CFX_Color& crRightBottom,
                                      BorderStyle nStyle,
                                      const CPWL_Dash& dash) {
  fxcrt::ostringstream sAppStream;
  ByteString sColor;

  float fLeft = rect.left;
  float fRight = rect.right;
  float fTop = rect.top;
  float fBottom = rect.bottom;

  if (fWidth > 0.0f) {
    float fHalfWidth = fWidth / 2.0f;
    AutoClosedQCommand q(&sAppStream);

    switch (nStyle) {
      default:
      case BorderStyle::kSolid:
        sColor = GetFillColorAppStream(color);
        if (sColor.GetLength() > 0) {
          sAppStream << sColor;
          WriteAppendRect(sAppStream, {fLeft, fBottom, fRight, fTop});
          WriteAppendRect(sAppStream, {fLeft + fWidth, fBottom + fWidth,
                                       fRight - fWidth, fTop - fWidth});
          sAppStream << kFillEvenOddOperator << "\n";
        }
        break;
      case BorderStyle::kDash:
        sColor = GetStrokeColorAppStream(color);
        if (sColor.GetLength() > 0) {
          sAppStream << sColor;
          sAppStream << fWidth << " " << kSetLineWidthOperator << " ["
                     << dash.nDash << " " << dash.nGap << "] " << dash.nPhase
                     << " " << kSetDashOperator << "\n";
          const CFX_PointF points[] = {
              {fLeft + fWidth / 2, fBottom + fWidth / 2},
              {fLeft + fWidth / 2, fTop - fWidth / 2},
              {fRight - fWidth / 2, fTop - fWidth / 2},
              {fRight - fWidth / 2, fBottom + fWidth / 2}};
          WriteClosedLoop(sAppStream, points);
          sAppStream << kStrokeOperator << "\n";
        }
        break;
      case BorderStyle::kBeveled:
      case BorderStyle::kInset:
        sColor = GetFillColorAppStream(crLeftTop);
        if (sColor.GetLength() > 0) {
          sAppStream << sColor;
          WriteMove(sAppStream, {fLeft + fHalfWidth, fBottom + fHalfWidth});
          WriteLine(sAppStream, {fLeft + fHalfWidth, fTop - fHalfWidth});
          WriteLine(sAppStream, {fRight - fHalfWidth, fTop - fHalfWidth});
          WriteLine(sAppStream,
                    {fRight - fHalfWidth * 2, fTop - fHalfWidth * 2});
          WriteLine(sAppStream,
                    {fLeft + fHalfWidth * 2, fTop - fHalfWidth * 2});
          WriteLine(sAppStream,
                    {fLeft + fHalfWidth * 2, fBottom + fHalfWidth * 2});
          sAppStream << kFillOperator << "\n";
        }
        sColor = GetFillColorAppStream(crRightBottom);
        if (sColor.GetLength() > 0) {
          sAppStream << sColor;
          WriteMove(sAppStream, {fRight - fHalfWidth, fTop - fHalfWidth});
          WriteLine(sAppStream, {fRight - fHalfWidth, fBottom + fHalfWidth});
          WriteLine(sAppStream, {fLeft + fHalfWidth, fBottom + fHalfWidth});
          WriteLine(sAppStream,
                    {fLeft + fHalfWidth * 2, fBottom + fHalfWidth * 2});
          WriteLine(sAppStream,
                    {fRight - fHalfWidth * 2, fBottom + fHalfWidth * 2});
          WriteLine(sAppStream,
                    {fRight - fHalfWidth * 2, fTop - fHalfWidth * 2});
          sAppStream << kFillOperator << "\n";
        }
        sColor = GetFillColorAppStream(color);
        if (sColor.GetLength() > 0) {
          sAppStream << sColor;
          WriteAppendRect(sAppStream, {fLeft, fBottom, fRight, fTop});
          WriteAppendRect(sAppStream, {fLeft + fHalfWidth, fBottom + fHalfWidth,
                                       fRight - fHalfWidth, fTop - fHalfWidth});
          sAppStream << kFillEvenOddOperator << "\n";
        }
        break;
      case BorderStyle::kUnderline:
        sColor = GetStrokeColorAppStream(color);
        if (sColor.GetLength() > 0) {
          sAppStream << sColor;
          sAppStream << fWidth << " " << kSetLineWidthOperator << "\n";
          WriteMove(sAppStream, {fLeft, fBottom + fWidth / 2});
          WriteLine(sAppStream, {fRight, fBottom + fWidth / 2});
          sAppStream << kStrokeOperator << "\n";
        }
        break;
    }
  }
  return ByteString(sAppStream);
}

ByteString GetDropButtonAppStream(const CFX_FloatRect& rcBBox) {
  if (rcBBox.IsEmpty())
    return ByteString();

  fxcrt::ostringstream sAppStream;
  {
    AutoClosedQCommand q(&sAppStream);
    sAppStream << GetFillColorAppStream(
        CFX_Color(CFX_Color::Type::kRGB, 220.0f / 255.0f, 220.0f / 255.0f,
                  220.0f / 255.0f));
    WriteAppendRect(sAppStream, rcBBox);
    sAppStream << kFillOperator << "\n";
  }

  {
    AutoClosedQCommand q(&sAppStream);
    sAppStream << GetBorderAppStreamInternal(
        rcBBox, 2, CFX_Color(CFX_Color::Type::kGray, 0),
        CFX_Color(CFX_Color::Type::kGray, 1),
        CFX_Color(CFX_Color::Type::kGray, 0.5), BorderStyle::kBeveled,
        CPWL_Dash(3, 0, 0));
  }

  CFX_PointF ptCenter = CFX_PointF((rcBBox.left + rcBBox.right) / 2,
                                   (rcBBox.top + rcBBox.bottom) / 2);
  if (FXSYS_IsFloatBigger(rcBBox.right - rcBBox.left, 6) &&
      FXSYS_IsFloatBigger(rcBBox.top - rcBBox.bottom, 6)) {
    AutoClosedQCommand q(&sAppStream);
    const CFX_PointF points[] = {{ptCenter.x - 3, ptCenter.y + 1.5f},
                                 {ptCenter.x + 3, ptCenter.y + 1.5f},
                                 {ptCenter.x, ptCenter.y - 1.5f}};
    sAppStream << " 0 " << kSetGrayOperator << "\n";
    WriteClosedLoop(sAppStream, points);
    sAppStream << kFillOperator << "\n";
  }

  return ByteString(sAppStream);
}

ByteString GetRectFillAppStream(const CFX_FloatRect& rect,
                                const CFX_Color& color) {
  fxcrt::ostringstream sAppStream;
  ByteString sColor = GetFillColorAppStream(color);
  if (sColor.GetLength() > 0) {
    AutoClosedQCommand q(&sAppStream);
    sAppStream << sColor;
    WriteAppendRect(sAppStream, rect);
    sAppStream << kFillOperator << "\n";
  }

  return ByteString(sAppStream);
}

void SetDefaultIconName(CPDF_Stream* pIcon, const char* name) {
  if (!pIcon)
    return;

  RetainPtr<CPDF_Dictionary> pImageDict = pIcon->GetMutableDict();
  if (!pImageDict)
    return;

  if (pImageDict->KeyExist("Name"))
    return;

  pImageDict->SetNewFor<CPDF_String>("Name", name, false);
}

absl::optional<CheckStyle> CheckStyleFromCaption(const WideString& caption) {
  if (caption.IsEmpty())
    return absl::nullopt;

  // Character values are ZapfDingbats encodings of named glyphs.
  switch (caption[0]) {
    case L'4':
      return CheckStyle::kCheck;
    case L'8':
      return CheckStyle::kCross;
    case L'H':
      return CheckStyle::kStar;
    case L'l':
      return CheckStyle::kCircle;
    case L'n':
      return CheckStyle::kSquare;
    case L'u':
      return CheckStyle::kDiamond;
    default:
      return absl::nullopt;
  }
}

}  // namespace

CPDFSDK_AppStream::CPDFSDK_AppStream(CPDFSDK_Widget* widget,
                                     CPDF_Dictionary* dict)
    : widget_(widget), dict_(dict) {}

CPDFSDK_AppStream::~CPDFSDK_AppStream() = default;

void CPDFSDK_AppStream::SetAsPushButton() {
  CPDF_FormControl* pControl = widget_->GetFormControl();
  CFX_FloatRect rcWindow = widget_->GetRotatedRect();
  ButtonStyle nLayout = ButtonStyle::kLabel;
  switch (pControl->GetTextPosition()) {
    case TEXTPOS_ICON:
      nLayout = ButtonStyle::kIcon;
      break;
    case TEXTPOS_BELOW:
      nLayout = ButtonStyle::kIconTopLabelBottom;
      break;
    case TEXTPOS_ABOVE:
      nLayout = ButtonStyle::kIconBottomLabelTop;
      break;
    case TEXTPOS_RIGHT:
      nLayout = ButtonStyle::kIconLeftLabelRight;
      break;
    case TEXTPOS_LEFT:
      nLayout = ButtonStyle::kIconRightLabelLeft;
      break;
    case TEXTPOS_OVERLAID:
      nLayout = ButtonStyle::kLabelOverIcon;
      break;
    default:
      nLayout = ButtonStyle::kLabel;
      break;
  }

  CFX_Color crBackground = pControl->GetOriginalBackgroundColor();
  CFX_Color crBorder = pControl->GetOriginalBorderColor();

  float fBorderWidth = static_cast<float>(widget_->GetBorderWidth());
  CPWL_Dash dsBorder(3, 0, 0);
  CFX_Color crLeftTop;
  CFX_Color crRightBottom;

  BorderStyle nBorderStyle = widget_->GetBorderStyle();
  switch (nBorderStyle) {
    case BorderStyle::kDash:
      dsBorder = CPWL_Dash(3, 3, 0);
      break;
    case BorderStyle::kBeveled:
      fBorderWidth *= 2;
      crLeftTop = CFX_Color(CFX_Color::Type::kGray, 1);
      crRightBottom = crBackground / 2.0f;
      break;
    case BorderStyle::kInset:
      fBorderWidth *= 2;
      crLeftTop = CFX_Color(CFX_Color::Type::kGray, 0.5);
      crRightBottom = CFX_Color(CFX_Color::Type::kGray, 0.75);
      break;
    default:
      break;
  }

  CFX_FloatRect rcClient = rcWindow.GetDeflated(fBorderWidth, fBorderWidth);
  CPDF_DefaultAppearance da = pControl->GetDefaultAppearance();
  absl::optional<CFX_Color> color = da.GetColor();
  CFX_Color crText = color.value_or(CFX_Color(CFX_Color::Type::kGray, 0));

  float fFontSize;
  ByteString csNameTag;
  absl::optional<ByteString> font = da.GetFont(&fFontSize);
  if (font.has_value())
    csNameTag = font.value();
  else
    fFontSize = 12.0f;

  WideString csWCaption;
  WideString csNormalCaption;
  WideString csRolloverCaption;
  WideString csDownCaption;
  if (pControl->HasMKEntry(pdfium::appearance::kCA))
    csNormalCaption = pControl->GetNormalCaption();

  if (pControl->HasMKEntry(pdfium::appearance::kRC))
    csRolloverCaption = pControl->GetRolloverCaption();

  if (pControl->HasMKEntry(pdfium::appearance::kAC))
    csDownCaption = pControl->GetDownCaption();

  RetainPtr<CPDF_Stream> pNormalIcon;
  RetainPtr<CPDF_Stream> pRolloverIcon;
  RetainPtr<CPDF_Stream> pDownIcon;
  if (pControl->HasMKEntry(pdfium::appearance::kI))
    pNormalIcon = pControl->GetNormalIcon();

  if (pControl->HasMKEntry(pdfium::appearance::kRI))
    pRolloverIcon = pControl->GetRolloverIcon();

  if (pControl->HasMKEntry(pdfium::appearance::kIX))
    pDownIcon = pControl->GetDownIcon();

  SetDefaultIconName(pNormalIcon.Get(), "ImgA");
  SetDefaultIconName(pRolloverIcon.Get(), "ImgB");
  SetDefaultIconName(pDownIcon.Get(), "ImgC");

  CPDF_IconFit iconFit = pControl->GetIconFit();
  {
    CPDF_BAFontMap font_map(widget_->GetPDFPage()->GetDocument(),
                            widget_->GetPDFAnnot()->GetMutableAnnotDict(), "N");
    ByteString csAP =
        GetRectFillAppStream(rcWindow, crBackground) +
        GetBorderAppStreamInternal(rcWindow, fBorderWidth, crBorder, crLeftTop,
                                   crRightBottom, nBorderStyle, dsBorder) +
        GetPushButtonAppStream(iconFit.GetFittingBounds() ? rcWindow : rcClient,
                               &font_map, pNormalIcon.Get(), iconFit,
                               csNormalCaption, crText, fFontSize, nLayout);

    Write("N", csAP, ByteString());
    if (pNormalIcon)
      AddImage("N", pNormalIcon.Get());

    CPDF_FormControl::HighlightingMode eHLM = pControl->GetHighlightingMode();
    if (eHLM != CPDF_FormControl::kPush && eHLM != CPDF_FormControl::kToggle) {
      Remove("D");
      Remove("R");
      return;
    }

    if (csRolloverCaption.IsEmpty() && !pRolloverIcon) {
      csRolloverCaption = csNormalCaption;
      pRolloverIcon = pNormalIcon;
    }
  }
  {
    CPDF_BAFontMap font_map(widget_->GetPDFPage()->GetDocument(),
                            widget_->GetPDFAnnot()->GetMutableAnnotDict(), "R");
    ByteString csAP =
        GetRectFillAppStream(rcWindow, crBackground) +
        GetBorderAppStreamInternal(rcWindow, fBorderWidth, crBorder, crLeftTop,
                                   crRightBottom, nBorderStyle, dsBorder) +
        GetPushButtonAppStream(iconFit.GetFittingBounds() ? rcWindow : rcClient,
                               &font_map, pRolloverIcon.Get(), iconFit,
                               csRolloverCaption, crText, fFontSize, nLayout);

    Write("R", csAP, ByteString());
    if (pRolloverIcon)
      AddImage("R", pRolloverIcon.Get());

    if (csDownCaption.IsEmpty() && !pDownIcon) {
      csDownCaption = csNormalCaption;
      pDownIcon = pNormalIcon;
    }

    switch (nBorderStyle) {
      case BorderStyle::kBeveled: {
        CFX_Color crTemp = crLeftTop;
        crLeftTop = crRightBottom;
        crRightBottom = crTemp;
        break;
      }
      case BorderStyle::kInset: {
        crLeftTop = CFX_Color(CFX_Color::Type::kGray, 0);
        crRightBottom = CFX_Color(CFX_Color::Type::kGray, 1);
        break;
      }
      default:
        break;
    }
  }
  {
    CPDF_BAFontMap font_map(widget_->GetPDFPage()->GetDocument(),
                            widget_->GetPDFAnnot()->GetMutableAnnotDict(), "D");
    ByteString csAP =
        GetRectFillAppStream(rcWindow, crBackground - 0.25f) +
        GetBorderAppStreamInternal(rcWindow, fBorderWidth, crBorder, crLeftTop,
                                   crRightBottom, nBorderStyle, dsBorder) +
        GetPushButtonAppStream(iconFit.GetFittingBounds() ? rcWindow : rcClient,
                               &font_map, pDownIcon.Get(), iconFit,
                               csDownCaption, crText, fFontSize, nLayout);

    Write("D", csAP, ByteString());
    if (pDownIcon)
      AddImage("D", pDownIcon.Get());
  }
}

void CPDFSDK_AppStream::SetAsCheckBox() {
  CPDF_FormControl* pControl = widget_->GetFormControl();
  CFX_Color crBackground = pControl->GetOriginalBackgroundColor();
  CFX_Color crBorder = pControl->GetOriginalBorderColor();
  float fBorderWidth = static_cast<float>(widget_->GetBorderWidth());
  CPWL_Dash dsBorder(3, 0, 0);
  CFX_Color crLeftTop;
  CFX_Color crRightBottom;

  BorderStyle nBorderStyle = widget_->GetBorderStyle();
  switch (nBorderStyle) {
    case BorderStyle::kDash:
      dsBorder = CPWL_Dash(3, 3, 0);
      break;
    case BorderStyle::kBeveled:
      fBorderWidth *= 2;
      crLeftTop = CFX_Color(CFX_Color::Type::kGray, 1);
      crRightBottom = crBackground / 2.0f;
      break;
    case BorderStyle::kInset:
      fBorderWidth *= 2;
      crLeftTop = CFX_Color(CFX_Color::Type::kGray, 0.5);
      crRightBottom = CFX_Color(CFX_Color::Type::kGray, 0.75);
      break;
    default:
      break;
  }

  CFX_FloatRect rcWindow = widget_->GetRotatedRect();
  CFX_FloatRect rcClient = rcWindow.GetDeflated(fBorderWidth, fBorderWidth);
  absl::optional<CFX_Color> color = pControl->GetDefaultAppearance().GetColor();
  CFX_Color crText = color.value_or(CFX_Color());

  CheckStyle nStyle = CheckStyleFromCaption(pControl->GetNormalCaption())
                          .value_or(CheckStyle::kCheck);
  ByteString csAP_N_ON =
      GetRectFillAppStream(rcWindow, crBackground) +
      GetBorderAppStreamInternal(rcWindow, fBorderWidth, crBorder, crLeftTop,
                                 crRightBottom, nBorderStyle, dsBorder);

  ByteString csAP_N_OFF = csAP_N_ON;

  switch (nBorderStyle) {
    case BorderStyle::kBeveled: {
      CFX_Color crTemp = crLeftTop;
      crLeftTop = crRightBottom;
      crRightBottom = crTemp;
      break;
    }
    case BorderStyle::kInset: {
      crLeftTop = CFX_Color(CFX_Color::Type::kGray, 0);
      crRightBottom = CFX_Color(CFX_Color::Type::kGray, 1);
      break;
    }
    default:
      break;
  }

  ByteString csAP_D_ON =
      GetRectFillAppStream(rcWindow, crBackground - 0.25f) +
      GetBorderAppStreamInternal(rcWindow, fBorderWidth, crBorder, crLeftTop,
                                 crRightBottom, nBorderStyle, dsBorder);

  ByteString csAP_D_OFF = csAP_D_ON;

  csAP_N_ON += GetCheckBoxAppStream(rcClient, nStyle, crText);
  csAP_D_ON += GetCheckBoxAppStream(rcClient, nStyle, crText);

  Write("N", csAP_N_ON, pControl->GetCheckedAPState());
  Write("N", csAP_N_OFF, "Off");

  Write("D", csAP_D_ON, pControl->GetCheckedAPState());
  Write("D", csAP_D_OFF, "Off");

  ByteString csAS = widget_->GetAppState();
  if (csAS.IsEmpty())
    widget_->SetAppStateOff();
}

void CPDFSDK_AppStream::SetAsRadioButton() {
  CPDF_FormControl* pControl = widget_->GetFormControl();
  CFX_Color crBackground = pControl->GetOriginalBackgroundColor();
  CFX_Color crBorder = pControl->GetOriginalBorderColor();
  float fBorderWidth = static_cast<float>(widget_->GetBorderWidth());
  CPWL_Dash dsBorder(3, 0, 0);
  CFX_Color crLeftTop;
  CFX_Color crRightBottom;

  BorderStyle nBorderStyle = widget_->GetBorderStyle();
  switch (nBorderStyle) {
    case BorderStyle::kDash:
      dsBorder = CPWL_Dash(3, 3, 0);
      break;
    case BorderStyle::kBeveled:
      fBorderWidth *= 2;
      crLeftTop = CFX_Color(CFX_Color::Type::kGray, 1);
      crRightBottom = crBackground / 2.0f;
      break;
    case BorderStyle::kInset:
      fBorderWidth *= 2;
      crLeftTop = CFX_Color(CFX_Color::Type::kGray, 0.5);
      crRightBottom = CFX_Color(CFX_Color::Type::kGray, 0.75);
      break;
    default:
      break;
  }

  CFX_FloatRect rcWindow = widget_->GetRotatedRect();
  CFX_FloatRect rcClient = rcWindow.GetDeflated(fBorderWidth, fBorderWidth);
  absl::optional<CFX_Color> color = pControl->GetDefaultAppearance().GetColor();
  CFX_Color crText = color.value_or(CFX_Color());
  CheckStyle nStyle = CheckStyleFromCaption(pControl->GetNormalCaption())
                          .value_or(CheckStyle::kCircle);

  ByteString csAP_N_ON;
  CFX_FloatRect rcCenter = rcWindow.GetCenterSquare().GetDeflated(1.0f, 1.0f);
  if (nStyle == CheckStyle::kCircle) {
    if (nBorderStyle == BorderStyle::kBeveled) {
      crLeftTop = CFX_Color(CFX_Color::Type::kGray, 1);
      crRightBottom = crBackground - 0.25f;
    } else if (nBorderStyle == BorderStyle::kInset) {
      crLeftTop = CFX_Color(CFX_Color::Type::kGray, 0.5f);
      crRightBottom = CFX_Color(CFX_Color::Type::kGray, 0.75f);
    }

    csAP_N_ON =
        GetCircleFillAppStream(rcCenter, crBackground) +
        GetCircleBorderAppStream(rcCenter, fBorderWidth, crBorder, crLeftTop,
                                 crRightBottom, nBorderStyle, dsBorder);
  } else {
    csAP_N_ON =
        GetRectFillAppStream(rcWindow, crBackground) +
        GetBorderAppStreamInternal(rcWindow, fBorderWidth, crBorder, crLeftTop,
                                   crRightBottom, nBorderStyle, dsBorder);
  }

  ByteString csAP_N_OFF = csAP_N_ON;

  switch (nBorderStyle) {
    case BorderStyle::kBeveled: {
      CFX_Color crTemp = crLeftTop;
      crLeftTop = crRightBottom;
      crRightBottom = crTemp;
      break;
    }
    case BorderStyle::kInset: {
      crLeftTop = CFX_Color(CFX_Color::Type::kGray, 0);
      crRightBottom = CFX_Color(CFX_Color::Type::kGray, 1);
      break;
    }
    default:
      break;
  }

  ByteString csAP_D_ON;

  if (nStyle == CheckStyle::kCircle) {
    CFX_Color crBK = crBackground - 0.25f;
    if (nBorderStyle == BorderStyle::kBeveled) {
      crLeftTop = crBackground - 0.25f;
      crRightBottom = CFX_Color(CFX_Color::Type::kGray, 1);
      crBK = crBackground;
    } else if (nBorderStyle == BorderStyle::kInset) {
      crLeftTop = CFX_Color(CFX_Color::Type::kGray, 0);
      crRightBottom = CFX_Color(CFX_Color::Type::kGray, 1);
    }

    csAP_D_ON =
        GetCircleFillAppStream(rcCenter, crBK) +
        GetCircleBorderAppStream(rcCenter, fBorderWidth, crBorder, crLeftTop,
                                 crRightBottom, nBorderStyle, dsBorder);
  } else {
    csAP_D_ON =
        GetRectFillAppStream(rcWindow, crBackground - 0.25f) +
        GetBorderAppStreamInternal(rcWindow, fBorderWidth, crBorder, crLeftTop,
                                   crRightBottom, nBorderStyle, dsBorder);
  }

  ByteString csAP_D_OFF = csAP_D_ON;

  ByteString app_stream = GetRadioButtonAppStream(rcClient, nStyle, crText);
  csAP_N_ON += app_stream;
  csAP_D_ON += app_stream;

  Write("N", csAP_N_ON, pControl->GetCheckedAPState());
  Write("N", csAP_N_OFF, "Off");

  Write("D", csAP_D_ON, pControl->GetCheckedAPState());
  Write("D", csAP_D_OFF, "Off");

  ByteString csAS = widget_->GetAppState();
  if (csAS.IsEmpty())
    widget_->SetAppStateOff();
}

void CPDFSDK_AppStream::SetAsComboBox(absl::optional<WideString> sValue) {
  CPDF_FormControl* pControl = widget_->GetFormControl();
  CPDF_FormField* pField = pControl->GetField();
  fxcrt::ostringstream sBody;

  CFX_FloatRect rcClient = widget_->GetClientRect();
  CFX_FloatRect rcButton = rcClient;
  rcButton.left = rcButton.right - 13;
  rcButton.Normalize();

  // Font map must outlive |pEdit|.
  CPDF_BAFontMap font_map(widget_->GetPDFPage()->GetDocument(),
                          widget_->GetPDFAnnot()->GetMutableAnnotDict(), "N");

  auto pEdit = std::make_unique<CPWL_EditImpl>();
  pEdit->EnableRefresh(false);
  pEdit->SetFontMap(&font_map);

  CFX_FloatRect rcEdit = rcClient;
  rcEdit.right = rcButton.left;
  rcEdit.Normalize();

  pEdit->SetPlateRect(rcEdit);
  pEdit->SetAlignmentV(1);

  float fFontSize = widget_->GetFontSize();
  if (FXSYS_IsFloatZero(fFontSize))
    pEdit->SetAutoFontSize(true);
  else
    pEdit->SetFontSize(fFontSize);

  pEdit->Initialize();
  if (sValue.has_value()) {
    pEdit->SetText(sValue.value());
  } else {
    int32_t nCurSel = pField->GetSelectedIndex(0);
    if (nCurSel < 0) {
      pEdit->SetText(pField->GetValue());
    } else {
      pEdit->SetText(pField->GetOptionLabel(nCurSel));
    }
  }
  pEdit->Paint();

  CFX_FloatRect rcContent = pEdit->GetContentRect();
  ByteString sEdit = GetEditAppStream(pEdit.get(), CFX_PointF(), true, 0);
  if (sEdit.GetLength() > 0) {
    sBody << "/Tx ";
    AutoClosedCommand bmc(&sBody, kMarkedSequenceBeginOperator,
                          kMarkedSequenceEndOperator);
    AutoClosedQCommand q(&sBody);

    if (rcContent.Width() > rcEdit.Width() ||
        rcContent.Height() > rcEdit.Height()) {
      WriteAppendRect(sBody, rcEdit);
      sBody << kSetNonZeroWindingClipOperator << "\n"
            << kEndPathNoFillOrStrokeOperator << "\n";
    }

    CFX_Color crText = widget_->GetTextPWLColor();
    AutoClosedCommand bt(&sBody, kTextBeginOperator, kTextEndOperator);
    sBody << GetFillColorAppStream(crText) << sEdit;
  }

  sBody << GetDropButtonAppStream(rcButton);
  Write("N",
        GetBackgroundAppStream() + GetBorderAppStream() + ByteString(sBody),
        ByteString());
}

void CPDFSDK_AppStream::SetAsListBox() {
  CPDF_FormControl* pControl = widget_->GetFormControl();
  CPDF_FormField* pField = pControl->GetField();
  CFX_FloatRect rcClient = widget_->GetClientRect();
  fxcrt::ostringstream sBody;

  // Font map must outlive |pEdit|.
  CPDF_BAFontMap font_map(widget_->GetPDFPage()->GetDocument(),
                          widget_->GetPDFAnnot()->GetMutableAnnotDict(), "N");

  auto pEdit = std::make_unique<CPWL_EditImpl>();
  pEdit->EnableRefresh(false);
  pEdit->SetFontMap(&font_map);
  pEdit->SetPlateRect(CFX_FloatRect(rcClient.left, 0.0f, rcClient.right, 0.0f));

  float fFontSize = widget_->GetFontSize();
  pEdit->SetFontSize(FXSYS_IsFloatZero(fFontSize) ? 12.0f : fFontSize);
  pEdit->Initialize();

  fxcrt::ostringstream sList;
  float fy = rcClient.top;

  int32_t nTop = pField->GetTopVisibleIndex();
  int32_t nCount = pField->CountOptions();
  int32_t nSelCount = pField->CountSelectedItems();

  for (int32_t i = nTop; i < nCount; ++i) {
    bool bSelected = false;
    for (int32_t j = 0; j < nSelCount; ++j) {
      if (pField->GetSelectedIndex(j) == i) {
        bSelected = true;
        break;
      }
    }

    pEdit->SetText(pField->GetOptionLabel(i));
    pEdit->Paint();

    CFX_FloatRect rcContent = pEdit->GetContentRect();
    float fItemHeight = rcContent.Height();

    if (bSelected) {
      CFX_FloatRect rcItem =
          CFX_FloatRect(rcClient.left, fy - fItemHeight, rcClient.right, fy);
      {
        AutoClosedQCommand q(&sList);
        sList << GetFillColorAppStream(CFX_Color(
            CFX_Color::Type::kRGB, 0, 51.0f / 255.0f, 113.0f / 255.0f));
        WriteAppendRect(sList, rcItem);
        sList << kFillOperator << "\n";
      }

      AutoClosedCommand bt(&sList, kTextBeginOperator, kTextEndOperator);
      sList << GetFillColorAppStream(CFX_Color(CFX_Color::Type::kGray, 1))
            << GetEditAppStream(pEdit.get(), CFX_PointF(0.0f, fy), true, 0);
    } else {
      CFX_Color crText = widget_->GetTextPWLColor();

      AutoClosedCommand bt(&sList, kTextBeginOperator, kTextEndOperator);
      sList << GetFillColorAppStream(crText)
            << GetEditAppStream(pEdit.get(), CFX_PointF(0.0f, fy), true, 0);
    }

    fy -= fItemHeight;
  }

  if (sList.tellp() > 0) {
    sBody << "/Tx ";
    AutoClosedCommand bmc(&sBody, kMarkedSequenceBeginOperator,
                          kMarkedSequenceEndOperator);
    AutoClosedQCommand q(&sBody);

    WriteAppendRect(sBody, rcClient);
    sBody << kSetNonZeroWindingClipOperator << "\n"
          << kEndPathNoFillOrStrokeOperator << "\n"
          << sList.str();
  }
  Write("N",
        GetBackgroundAppStream() + GetBorderAppStream() + ByteString(sBody),
        ByteString());
}

void CPDFSDK_AppStream::SetAsTextField(absl::optional<WideString> sValue) {
  CPDF_FormControl* pControl = widget_->GetFormControl();
  CPDF_FormField* pField = pControl->GetField();
  fxcrt::ostringstream sBody;
  fxcrt::ostringstream sLines;

  // Font map must outlive |pEdit|.
  CPDF_BAFontMap font_map(widget_->GetPDFPage()->GetDocument(),
                          widget_->GetPDFAnnot()->GetMutableAnnotDict(), "N");

  auto pEdit = std::make_unique<CPWL_EditImpl>();
  pEdit->EnableRefresh(false);
  pEdit->SetFontMap(&font_map);

  CFX_FloatRect rcClient = widget_->GetClientRect();
  pEdit->SetPlateRect(rcClient);
  pEdit->SetAlignmentH(pControl->GetControlAlignment());

  uint32_t dwFieldFlags = pField->GetFieldFlags();
  bool bMultiLine = dwFieldFlags & pdfium::form_flags::kTextMultiline;
  if (bMultiLine) {
    pEdit->SetMultiLine(true);
    pEdit->SetAutoReturn(true);
  } else {
    pEdit->SetAlignmentV(1);
  }

  uint16_t subWord = 0;
  if (dwFieldFlags & pdfium::form_flags::kTextPassword) {
    subWord = '*';
    pEdit->SetPasswordChar(subWord);
  }

  int nMaxLen = pField->GetMaxLen();
  bool bCharArray = dwFieldFlags & pdfium::form_flags::kTextComb;
  float fFontSize = widget_->GetFontSize();

#ifdef PDF_ENABLE_XFA
  if (!sValue.has_value() && widget_->GetMixXFAWidget())
    sValue = widget_->GetValue();
#endif  // PDF_ENABLE_XFA

  if (nMaxLen > 0) {
    if (bCharArray) {
      pEdit->SetCharArray(nMaxLen);
      if (FXSYS_IsFloatZero(fFontSize)) {
        fFontSize = CPWL_Edit::GetCharArrayAutoFontSize(
            font_map.GetPDFFont(0).Get(), rcClient, nMaxLen);
      }
    } else {
      if (sValue.has_value())
        nMaxLen = pdfium::base::checked_cast<int>(sValue.value().GetLength());
      pEdit->SetLimitChar(nMaxLen);
    }
  }

  if (FXSYS_IsFloatZero(fFontSize))
    pEdit->SetAutoFontSize(true);
  else
    pEdit->SetFontSize(fFontSize);

  pEdit->Initialize();
  pEdit->SetText(sValue.value_or(pField->GetValue()));
  pEdit->Paint();

  CFX_FloatRect rcContent = pEdit->GetContentRect();
  ByteString sEdit =
      GetEditAppStream(pEdit.get(), CFX_PointF(), !bCharArray, subWord);

  if (sEdit.GetLength() > 0) {
    sBody << "/Tx ";
    AutoClosedCommand bmc(&sBody, kMarkedSequenceBeginOperator,
                          kMarkedSequenceEndOperator);
    AutoClosedQCommand q(&sBody);

    if (rcContent.Width() > rcClient.Width() ||
        rcContent.Height() > rcClient.Height()) {
      WriteAppendRect(sBody, rcClient);
      sBody << kSetNonZeroWindingClipOperator << "\n"
            << kEndPathNoFillOrStrokeOperator << "\n";
    }
    CFX_Color crText = widget_->GetTextPWLColor();

    AutoClosedCommand bt(&sBody, kTextBeginOperator, kTextEndOperator);
    sBody << GetFillColorAppStream(crText) << sEdit;
  }

  if (bCharArray) {
    switch (widget_->GetBorderStyle()) {
      case BorderStyle::kSolid: {
        ByteString sColor =
            GetStrokeColorAppStream(widget_->GetBorderPWLColor());
        if (sColor.GetLength() > 0) {
          AutoClosedQCommand q(&sLines);
          sLines << widget_->GetBorderWidth() << " " << kSetLineWidthOperator
                 << "\n"
                 << GetStrokeColorAppStream(widget_->GetBorderPWLColor())
                 << " 2 " << kSetLineCapStyleOperator << " 0 "
                 << kSetLineJoinStyleOperator << "\n";

          const float width = rcClient.right - rcClient.left;
          for (int32_t i = 1; i < nMaxLen; ++i) {
            const float left = rcClient.left + (width / nMaxLen) * i;
            WriteMove(sLines, {left, rcClient.bottom});
            WriteLine(sLines, {left, rcClient.top});
            sLines << kStrokeOperator << "\n";
          }
        }
        break;
      }
      case BorderStyle::kDash: {
        ByteString sColor =
            GetStrokeColorAppStream(widget_->GetBorderPWLColor());
        if (sColor.GetLength() > 0) {
          CPWL_Dash dsBorder = CPWL_Dash(3, 3, 0);
          AutoClosedQCommand q(&sLines);
          sLines << widget_->GetBorderWidth() << " " << kSetLineWidthOperator
                 << "\n"
                 << GetStrokeColorAppStream(widget_->GetBorderPWLColor()) << "["
                 << dsBorder.nDash << " " << dsBorder.nGap << "] "
                 << dsBorder.nPhase << " " << kSetDashOperator << "\n";

          const float width = rcClient.right - rcClient.left;
          for (int32_t i = 1; i < nMaxLen; ++i) {
            const float left = rcClient.left + (width / nMaxLen) * i;
            WriteMove(sLines, {left, rcClient.bottom});
            WriteLine(sLines, {left, rcClient.top});
            sLines << kStrokeOperator << "\n";
          }
        }
        break;
      }
      default:
        break;
    }
  }

  Write("N",
        GetBackgroundAppStream() + GetBorderAppStream() + ByteString(sLines) +
            ByteString(sBody),
        ByteString());
}

void CPDFSDK_AppStream::AddImage(const ByteString& sAPType,
                                 CPDF_Stream* pImage) {
  RetainPtr<CPDF_Stream> pStream = dict_->GetMutableStreamFor(sAPType);
  RetainPtr<CPDF_Dictionary> pStreamDict = pStream->GetMutableDict();
  ByteString sImageAlias = "IMG";

  const CPDF_Dictionary* pImageDict = pImage->GetDict();
  if (pImageDict)
    sImageAlias = pImageDict->GetStringFor("Name");

  RetainPtr<CPDF_Dictionary> pStreamResList =
      pStreamDict->GetOrCreateDictFor("Resources");
  CPDF_Dictionary* pXObject =
      pStreamResList->SetNewFor<CPDF_Dictionary>("XObject");
  pXObject->SetNewFor<CPDF_Reference>(sImageAlias,
                                      widget_->GetPageView()->GetPDFDocument(),
                                      pImage->GetObjNum());
}

void CPDFSDK_AppStream::Write(const ByteString& sAPType,
                              const ByteString& sContents,
                              const ByteString& sAPState) {
  RetainPtr<CPDF_Dictionary> pParentDict;
  ByteString key;
  if (sAPState.IsEmpty()) {
    pParentDict = dict_.Get();
    key = sAPType;
  } else {
    pParentDict = dict_->GetOrCreateDictFor(sAPType);
    key = sAPState;
  }

  RetainPtr<CPDF_Dictionary> pOrigStreamDict;

  // If `pStream` is created by CreateModifiedAPStream(), then it is safe to
  // edit, as it is not shared.
  RetainPtr<CPDF_Stream> pStream = pParentDict->GetMutableStreamFor(key);
  CPDF_Document* doc = widget_->GetPageView()->GetPDFDocument();
  if (!doc->IsModifiedAPStream(pStream.Get())) {
    if (pStream)
      pOrigStreamDict = pStream->GetMutableDict();
    pStream = doc->CreateModifiedAPStream();
    pParentDict->SetNewFor<CPDF_Reference>(key, doc, pStream->GetObjNum());
  }

  RetainPtr<CPDF_Dictionary> pStreamDict = pStream->GetMutableDict();
  if (!pStreamDict) {
    auto pNewDict =
        widget_->GetPDFAnnot()->GetDocument()->New<CPDF_Dictionary>();
    pStreamDict = pNewDict.Get();
    pStreamDict->SetNewFor<CPDF_Name>("Type", "XObject");
    pStreamDict->SetNewFor<CPDF_Name>("Subtype", "Form");
    pStreamDict->SetNewFor<CPDF_Number>("FormType", 1);

    if (pOrigStreamDict) {
      const CPDF_Dictionary* pResources =
          pOrigStreamDict->GetDictFor("Resources");
      if (pResources)
        pStreamDict->SetFor("Resources", pResources->Clone());
    }

    pStream->InitStream({}, std::move(pNewDict));
  }
  pStreamDict->SetMatrixFor("Matrix", widget_->GetMatrix());
  pStreamDict->SetRectFor("BBox", widget_->GetRotatedRect());
  pStream->SetDataAndRemoveFilter(sContents.raw_span());
}

void CPDFSDK_AppStream::Remove(ByteStringView sAPType) {
  dict_->RemoveFor(sAPType);
}

ByteString CPDFSDK_AppStream::GetBackgroundAppStream() const {
  CFX_Color crBackground = widget_->GetFillPWLColor();
  if (crBackground.nColorType != CFX_Color::Type::kTransparent)
    return GetRectFillAppStream(widget_->GetRotatedRect(), crBackground);

  return ByteString();
}

ByteString CPDFSDK_AppStream::GetBorderAppStream() const {
  CFX_FloatRect rcWindow = widget_->GetRotatedRect();
  CFX_Color crBorder = widget_->GetBorderPWLColor();
  CFX_Color crBackground = widget_->GetFillPWLColor();
  CFX_Color crLeftTop;
  CFX_Color crRightBottom;

  float fBorderWidth = static_cast<float>(widget_->GetBorderWidth());
  CPWL_Dash dsBorder(3, 0, 0);

  BorderStyle nBorderStyle = widget_->GetBorderStyle();
  switch (nBorderStyle) {
    case BorderStyle::kDash:
      dsBorder = CPWL_Dash(3, 3, 0);
      break;
    case BorderStyle::kBeveled:
      fBorderWidth *= 2;
      crLeftTop = CFX_Color(CFX_Color::Type::kGray, 1);
      crRightBottom = crBackground / 2.0f;
      break;
    case BorderStyle::kInset:
      fBorderWidth *= 2;
      crLeftTop = CFX_Color(CFX_Color::Type::kGray, 0.5);
      crRightBottom = CFX_Color(CFX_Color::Type::kGray, 0.75);
      break;
    default:
      break;
  }

  return GetBorderAppStreamInternal(rcWindow, fBorderWidth, crBorder, crLeftTop,
                                    crRightBottom, nBorderStyle, dsBorder);
}
