cpdf_dictionary.h revision 4d3acf4ec42bf6e838f9060103aff98fbf170794
1// Copyright 2016 PDFium Authors. All rights reserved.
2// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
4
5// Original code copyright 2014 Foxit Software Inc. http://www.foxitsoftware.com
6
7#ifndef CORE_FPDFAPI_PARSER_CPDF_DICTIONARY_H_
8#define CORE_FPDFAPI_PARSER_CPDF_DICTIONARY_H_
9
10#include <map>
11#include <memory>
12#include <set>
13#include <utility>
14
15#include "core/fpdfapi/parser/cpdf_object.h"
16#include "core/fxcrt/cfx_string_pool_template.h"
17#include "core/fxcrt/cfx_weak_ptr.h"
18#include "core/fxcrt/fx_coordinates.h"
19#include "core/fxcrt/fx_string.h"
20#include "third_party/base/ptr_util.h"
21
22class CPDF_IndirectObjectHolder;
23
24class CPDF_Dictionary : public CPDF_Object {
25 public:
26  using const_iterator =
27      std::map<CFX_ByteString, std::unique_ptr<CPDF_Object>>::const_iterator;
28
29  CPDF_Dictionary();
30  explicit CPDF_Dictionary(const CFX_WeakPtr<CFX_ByteStringPool>& pPool);
31  ~CPDF_Dictionary() override;
32
33  // CPDF_Object:
34  Type GetType() const override;
35  std::unique_ptr<CPDF_Object> Clone() const override;
36  CPDF_Dictionary* GetDict() const override;
37  bool IsDictionary() const override;
38  CPDF_Dictionary* AsDictionary() override;
39  const CPDF_Dictionary* AsDictionary() const override;
40
41  size_t GetCount() const { return m_Map.size(); }
42  CPDF_Object* GetObjectFor(const CFX_ByteString& key) const;
43  CPDF_Object* GetDirectObjectFor(const CFX_ByteString& key) const;
44  CFX_ByteString GetStringFor(const CFX_ByteString& key) const;
45  CFX_ByteString GetStringFor(const CFX_ByteString& key,
46                              const CFX_ByteString& default_str) const;
47  CFX_WideString GetUnicodeTextFor(const CFX_ByteString& key) const;
48  int GetIntegerFor(const CFX_ByteString& key) const;
49  int GetIntegerFor(const CFX_ByteString& key, int default_int) const;
50  bool GetBooleanFor(const CFX_ByteString& key, bool bDefault = false) const;
51  FX_FLOAT GetNumberFor(const CFX_ByteString& key) const;
52  CPDF_Dictionary* GetDictFor(const CFX_ByteString& key) const;
53  CPDF_Stream* GetStreamFor(const CFX_ByteString& key) const;
54  CPDF_Array* GetArrayFor(const CFX_ByteString& key) const;
55  CFX_FloatRect GetRectFor(const CFX_ByteString& key) const;
56  CFX_Matrix GetMatrixFor(const CFX_ByteString& key) const;
57  FX_FLOAT GetFloatFor(const CFX_ByteString& key) const {
58    return GetNumberFor(key);
59  }
60
61  bool KeyExist(const CFX_ByteString& key) const;
62  bool IsSignatureDict() const;
63
64  // Set* functions invalidate iterators for the element with the key |key|.
65  // Takes ownership of |pObj|, returns an unowned pointer to it.
66  CPDF_Object* SetFor(const CFX_ByteString& key,
67                      std::unique_ptr<CPDF_Object> pObj);
68
69  // Creates a new object owned by the dictionary and returns an unowned
70  // pointer to it.
71  template <typename T, typename... Args>
72  typename std::enable_if<!CanInternStrings<T>::value, T*>::type SetNewFor(
73      const CFX_ByteString& key,
74      Args&&... args) {
75    return static_cast<T*>(
76        SetFor(key, pdfium::MakeUnique<T>(std::forward<Args>(args)...)));
77  }
78  template <typename T, typename... Args>
79  typename std::enable_if<CanInternStrings<T>::value, T*>::type SetNewFor(
80      const CFX_ByteString& key,
81      Args&&... args) {
82    return static_cast<T*>(SetFor(
83        key, pdfium::MakeUnique<T>(m_pPool, std::forward<Args>(args)...)));
84  }
85
86  // Convenience functions to convert native objects to array form.
87  void SetRectFor(const CFX_ByteString& key, const CFX_FloatRect& rect);
88  void SetMatrixFor(const CFX_ByteString& key, const CFX_Matrix& matrix);
89
90  void ConvertToIndirectObjectFor(const CFX_ByteString& key,
91                                  CPDF_IndirectObjectHolder* pHolder);
92
93  // Invalidates iterators for the element with the key |key|.
94  void RemoveFor(const CFX_ByteString& key);
95
96  // Invalidates iterators for the element with the key |oldkey|.
97  void ReplaceKey(const CFX_ByteString& oldkey, const CFX_ByteString& newkey);
98
99  const_iterator begin() const { return m_Map.begin(); }
100  const_iterator end() const { return m_Map.end(); }
101
102  CFX_WeakPtr<CFX_ByteStringPool> GetByteStringPool() const { return m_pPool; }
103
104 protected:
105  CFX_ByteString MaybeIntern(const CFX_ByteString& str);
106  std::unique_ptr<CPDF_Object> CloneNonCyclic(
107      bool bDirect,
108      std::set<const CPDF_Object*>* visited) const override;
109
110  CFX_WeakPtr<CFX_ByteStringPool> m_pPool;
111  std::map<CFX_ByteString, std::unique_ptr<CPDF_Object>> m_Map;
112};
113
114inline CPDF_Dictionary* ToDictionary(CPDF_Object* obj) {
115  return obj ? obj->AsDictionary() : nullptr;
116}
117
118inline const CPDF_Dictionary* ToDictionary(const CPDF_Object* obj) {
119  return obj ? obj->AsDictionary() : nullptr;
120}
121
122inline std::unique_ptr<CPDF_Dictionary> ToDictionary(
123    std::unique_ptr<CPDF_Object> obj) {
124  CPDF_Dictionary* pDict = ToDictionary(obj.get());
125  if (!pDict)
126    return nullptr;
127  obj.release();
128  return std::unique_ptr<CPDF_Dictionary>(pDict);
129}
130
131#endif  // CORE_FPDFAPI_PARSER_CPDF_DICTIONARY_H_
132