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

#include "core/include/fpdfdoc/fpdf_doc.h"

#include <vector>

#include "core/fpdfapi/fpdf_parser/include/cpdf_array.h"
#include "core/include/fpdfapi/fpdf_page.h"

CPDF_LinkList::CPDF_LinkList() {}

CPDF_LinkList::~CPDF_LinkList() {}

const std::vector<CPDF_Dictionary*>* CPDF_LinkList::GetPageLinks(
    CPDF_Page* pPage) {
  FX_DWORD objnum = pPage->m_pFormDict->GetObjNum();
  if (objnum == 0)
    return nullptr;

  auto it = m_PageMap.find(objnum);
  if (it != m_PageMap.end())
    return &it->second;

  // std::map::operator[] forces the creation of a map entry.
  std::vector<CPDF_Dictionary*>& page_link_list = m_PageMap[objnum];
  LoadPageLinks(pPage, &page_link_list);
  return &page_link_list;
}

CPDF_Link CPDF_LinkList::GetLinkAtPoint(CPDF_Page* pPage,
                                        FX_FLOAT pdf_x,
                                        FX_FLOAT pdf_y,
                                        int* z_order) {
  const std::vector<CPDF_Dictionary*>* pPageLinkList = GetPageLinks(pPage);
  if (!pPageLinkList)
    return CPDF_Link();

  for (size_t i = pPageLinkList->size(); i > 0; --i) {
    size_t annot_index = i - 1;
    CPDF_Dictionary* pAnnot = (*pPageLinkList)[annot_index];
    if (!pAnnot)
      continue;

    CPDF_Link link(pAnnot);
    CFX_FloatRect rect = link.GetRect();
    if (!rect.Contains(pdf_x, pdf_y))
      continue;

    if (z_order)
      *z_order = annot_index;
    return link;
  }
  return CPDF_Link();
}

void CPDF_LinkList::LoadPageLinks(CPDF_Page* pPage,
                                  std::vector<CPDF_Dictionary*>* pList) {
  CPDF_Array* pAnnotList = pPage->m_pFormDict->GetArrayBy("Annots");
  if (!pAnnotList)
    return;

  for (FX_DWORD i = 0; i < pAnnotList->GetCount(); ++i) {
    CPDF_Dictionary* pAnnot = pAnnotList->GetDictAt(i);
    bool add_link = (pAnnot && pAnnot->GetStringBy("Subtype") == "Link");
    // Add non-links as nullptrs to preserve z-order.
    pList->push_back(add_link ? pAnnot : nullptr);
  }
}

CFX_FloatRect CPDF_Link::GetRect() {
  return m_pDict->GetRectBy("Rect");
}
CPDF_Dest CPDF_Link::GetDest(CPDF_Document* pDoc) {
  CPDF_Object* pDest = m_pDict->GetElementValue("Dest");
  if (!pDest)
    return CPDF_Dest();

  if (pDest->IsString() || pDest->IsName()) {
    CPDF_NameTree name_tree(pDoc, "Dests");
    CFX_ByteStringC name = pDest->GetString();
    return CPDF_Dest(name_tree.LookupNamedDest(pDoc, name));
  }
  if (CPDF_Array* pArray = pDest->AsArray())
    return CPDF_Dest(pArray);
  return CPDF_Dest();
}
CPDF_Action CPDF_Link::GetAction() {
  return CPDF_Action(m_pDict->GetDictBy("A"));
}
