PoDoFo  1.0.0-dev
PdfDictionary.h
1 
7 #ifndef PDF_DICTIONARY_H
8 #define PDF_DICTIONARY_H
9 
10 #include "PdfDeclarations.h"
11 #include "PdfDataContainer.h"
12 
13 namespace PoDoFo {
14 
15 class PdfDictionary;
16 
20 template <typename TObject, typename TMapIterator>
21 class PdfDictionaryIndirectIterableBase final : public PdfIndirectIterableBase
22 {
23  friend class PdfDictionary;
24 
25 public:
27 
28 private:
30 
31 public:
32  class Iterator final
33  {
35  public:
36  using difference_type = void;
37  using value_type = std::pair<PdfName, TObject*>;
38  using pointer = const value_type*;
39  using reference = const value_type&;
40  using iterator_category = std::forward_iterator_tag;
41  public:
42  Iterator();
43  private:
44  Iterator(TMapIterator&& iterator, PdfIndirectObjectList* objects);
45  public:
46  Iterator(const Iterator&) = default;
47  Iterator& operator=(const Iterator&) = default;
48  bool operator==(const Iterator& rhs) const;
49  bool operator!=(const Iterator& rhs) const;
50  Iterator& operator++();
51  Iterator operator++(int);
52  reference operator*();
53  pointer operator->();
54  private:
55  void resolve();
56  private:
57  TMapIterator m_iterator;
58  PdfIndirectObjectList* m_objects;
59  value_type m_pair;
60  };
61 
62 public:
63  Iterator begin() const;
64  Iterator end() const;
65 
66 private:
67  PdfDictionary* m_dict;
68 };
69 
72 
81 class PODOFO_API PdfDictionary final : public PdfDataContainer
82 {
83  friend class PdfObject;
84  friend class PdfTokenizer;
85  friend class PdfSignature;
86  friend class PdfObjectStream;
87  friend class PdfObjectOutputStream;
88 
89 public:
92  PdfDictionary();
93 
97  PdfDictionary(const PdfDictionary& rhs);
98  PdfDictionary(PdfDictionary&& rhs) noexcept;
99 
111  PdfDictionary& operator=(const PdfDictionary& rhs);
112  PdfDictionary& operator=(PdfDictionary&& rhs) noexcept;
113 
119  bool operator==(const PdfDictionary& rhs) const;
120 
124  bool operator!=(const PdfDictionary& rhs) const;
125 
128  void Clear();
129 
140  PdfObject& AddKey(const PdfName& key, const PdfObject& obj);
141  PdfObject& AddKey(const PdfName& key, PdfObject&& obj);
142 
156  void AddKeyIndirect(const PdfName& key, const PdfObject& obj);
157 
171  PdfObject& AddKeyIndirectSafe(const PdfName& key, const PdfObject& obj);
172 
182  const PdfObject* GetKey(const std::string_view& key) const;
183 
195  PdfObject* GetKey(const std::string_view& key);
196 
206  const PdfObject* FindKey(const std::string_view& key) const;
207  PdfObject* FindKey(const std::string_view& key);
208  const PdfObject& MustFindKey(const std::string_view& key) const;
209  PdfObject& MustFindKey(const std::string_view& key);
210 
221  const PdfObject* FindKeyParent(const std::string_view& key) const;
222  PdfObject* FindKeyParent(const std::string_view& key);
223  const PdfObject& MustFindKeyParent(const std::string_view& key) const;
224  PdfObject& MustFindKeyParent(const std::string_view& key);
225 
239  const PdfObject& MustGetKey(const std::string_view& key) const;
240  PdfObject& MustGetKey(const std::string_view& key);
241 
242  template <typename T>
243  T GetKeyAs(const std::string_view& key, const std::common_type_t<T>& defvalue = { }) const;
244 
245  template <typename T>
246  T FindKeyAs(const std::string_view& key, const std::common_type_t<T>& defvalue = { }) const;
247 
248  template <typename T>
249  T FindKeyParentAs(const std::string_view& key, const std::common_type_t<T>& defvalue = { }) const;
250 
251  template <typename T>
252  T FindKeyAsSafe(const std::string_view& key, const std::common_type_t<T>& defvalue = { }) const;
253 
254  template <typename T>
255  T FindKeyParentAsSafe(const std::string_view& key, const std::common_type_t<T>& defvalue = { }) const;
256 
257  template <typename T>
258  bool TryFindKeyAs(const std::string_view& key, T& value) const;
259 
260  template <typename T>
261  bool TryFindKeyParentAs(const std::string_view& key, T& value) const;
262 
268  bool HasKey(const std::string_view& key) const;
269 
281  bool RemoveKey(const std::string_view& key);
282 
283  void Write(OutputStream& stream, PdfWriteFlags writeMode,
284  const PdfStatefulEncrypt* encrypt, charbuff& buffer) const override;
285 
289  unsigned GetSize() const;
290 
291  PdfDictionaryIndirectIterable GetIndirectIterator();
292 
293  PdfDictionaryConstIndirectIterable GetIndirectIterator() const;
294 
295 public:
296  using iterator = PdfNameMap<PdfObject>::iterator;
297  using const_iterator = PdfNameMap<PdfObject>::const_iterator;
298 
299 public:
300  iterator begin();
301  iterator end();
302  const_iterator begin() const;
303  const_iterator end() const;
304  size_t size() const;
305 
306 protected:
307  void resetDirty() override;
308  void setChildrenParent() override;
309 
310 private:
311  // NOTE: It also doesn't dirty set the moved "obj"
312  void AddKeyNoDirtySet(const PdfName& key, PdfObject&& obj);
313  void AddKeyNoDirtySet(const PdfName& key, PdfVariant&& var);
314  void RemoveKeyNoDirtySet(const std::string_view& key);
315  // Append a new "null" object with the given key
316  PdfObject& EmplaceNoDirtySet(const PdfName& key);
317 
318 private:
319  PdfObject& addKey(const PdfName& key, PdfObject&& obj);
320  PdfObject* getKey(const std::string_view& key) const;
321  PdfObject* findKey(const std::string_view& key) const;
322  PdfObject* findKeyParent(const std::string_view& key) const;
323  void write(OutputStream& stream, PdfWriteFlags writeMode, bool addDelimiters,
324  const PdfStatefulEncrypt* encrypt, charbuff& buffer) const;
325 
326 private:
327  PdfNameMap<PdfObject> m_Map;
328 };
329 
330 template<typename T>
331 T PdfDictionary::GetKeyAs(const std::string_view& key, const std::common_type_t<T>& defvalue) const
332 {
333  auto obj = getKey(key);
334  if (obj == nullptr)
335  return defvalue;
336 
337  return Object<T>::Get(*obj);
338 }
339 
340 template<typename T>
341 T PdfDictionary::FindKeyAs(const std::string_view& key, const std::common_type_t<T>& defvalue) const
342 {
343  auto obj = findKey(key);
344  if (obj == nullptr)
345  return defvalue;
346 
347  return Object<T>::Get(*obj);
348 }
349 
350 template<typename T>
351 T PdfDictionary::FindKeyParentAs(const std::string_view& key, const std::common_type_t<T>& defvalue) const
352 {
353  auto obj = findKeyParent(key);
354  T ret{ };
355  if (obj == nullptr)
356  return defvalue;
357 
358  return Object<T>::Get(*obj);
359 }
360 
361 template<typename T>
362 T PdfDictionary::FindKeyAsSafe(const std::string_view& key, const std::common_type_t<T>& defvalue) const
363 {
364  T value;
365  auto obj = findKey(key);
366  if (obj != nullptr && Object<T>::TryGet(*obj, value))
367  return value;
368  else
369  return defvalue;
370 }
371 
372 template<typename T>
373 T PdfDictionary::FindKeyParentAsSafe(const std::string_view& key, const std::common_type_t<T>& defvalue) const
374 {
375  T value;
376  auto obj = findKeyParent(key);
377  if (obj != nullptr && Object<T>::TryGet(*obj, value))
378  return value;
379  else
380  return defvalue;
381 }
382 
383 template <typename T>
384 bool PdfDictionary::TryFindKeyAs(const std::string_view& key, T& value) const
385 {
386  auto obj = findKey(key);
387  if (obj != nullptr && Object<T>::TryGet(*obj, value))
388  {
389  return true;
390  }
391  else
392  {
393  value = { };
394  return false;
395  }
396 }
397 
398 template <typename T>
399 bool PdfDictionary::TryFindKeyParentAs(const std::string_view& key, T& value) const
400 {
401  auto obj = findKeyParent(key);
402  if (obj != nullptr && Object<T>::TryGet(*obj, value))
403  {
404  return true;
405  }
406  else
407  {
408  value = { };
409  return false;
410  }
411 }
412 
413 template <typename TObject, typename TMapIterator>
414 PdfDictionaryIndirectIterableBase<TObject, TMapIterator>::PdfDictionaryIndirectIterableBase()
415  : m_dict(nullptr) { }
416 
417 template <typename TObject, typename TMapIterator>
418 PdfDictionaryIndirectIterableBase<TObject, TMapIterator>::PdfDictionaryIndirectIterableBase(PdfDictionary& dict)
419  : PdfIndirectIterableBase(dict), m_dict(&dict) { }
420 
421 template <typename TObject, typename TMapIterator>
422 typename PdfDictionaryIndirectIterableBase<TObject, TMapIterator>::Iterator PdfDictionaryIndirectIterableBase<TObject, TMapIterator>::begin() const
423 {
424  if (m_dict == nullptr)
425  return Iterator();
426  else
427  return Iterator(m_dict->begin(), GetObjects());
428 }
429 
430 template <typename TObject, typename TMapIterator>
431 typename PdfDictionaryIndirectIterableBase<TObject, TMapIterator>::Iterator PdfDictionaryIndirectIterableBase<TObject, TMapIterator>::end() const
432 {
433  if (m_dict == nullptr)
434  return Iterator();
435  else
436  return Iterator(m_dict->end(), GetObjects());
437 }
438 
439 template<typename TObject, typename TMapIterator>
440 PdfDictionaryIndirectIterableBase<TObject, TMapIterator>::Iterator::Iterator() : m_objects(nullptr) { }
441 
442 template<typename TObject, typename TMapIterator>
443 PdfDictionaryIndirectIterableBase<TObject, TMapIterator>::Iterator::Iterator(TMapIterator&& iterator, PdfIndirectObjectList* objects)
444  : m_iterator(std::move(iterator)), m_objects(objects) { }
445 
446 template<typename TObject, typename TMapIterator>
447 bool PdfDictionaryIndirectIterableBase<TObject, TMapIterator>::Iterator::operator==(const Iterator& rhs) const
448 {
449  return m_iterator == rhs.m_iterator;
450 }
451 
452 template<typename TObject, typename TMapIterator>
453 bool PdfDictionaryIndirectIterableBase<TObject, TMapIterator>::Iterator::operator!=(const Iterator& rhs) const
454 {
455  return m_iterator != rhs.m_iterator;
456 }
457 
458 template<typename TObject, typename TMapIterator>
459 typename PdfDictionaryIndirectIterableBase<TObject, TMapIterator>::Iterator& PdfDictionaryIndirectIterableBase<TObject, TMapIterator>::Iterator::operator++()
460 {
461  m_iterator++;
462  return *this;
463 }
464 
465 template<typename TObject, typename TMapIterator>
466 typename PdfDictionaryIndirectIterableBase<TObject, TMapIterator>::Iterator PdfDictionaryIndirectIterableBase<TObject, TMapIterator>::Iterator::operator++(int)
467 {
468  auto copy = *this;
469  m_iterator++;
470  return copy;
471 }
472 
473 template<typename TObject, typename TMapIterator>
474 typename PdfDictionaryIndirectIterableBase<TObject, TMapIterator>::Iterator::reference PdfDictionaryIndirectIterableBase<TObject, TMapIterator>::Iterator::operator*()
475 {
476  resolve();
477  return m_pair;
478 }
479 
480 template<typename TObject, typename TMapIterator>
481 typename PdfDictionaryIndirectIterableBase<TObject, TMapIterator>::Iterator::pointer PdfDictionaryIndirectIterableBase<TObject, TMapIterator>::Iterator::operator->()
482 {
483  resolve();
484  return &m_pair;
485 }
486 
487 template<typename TObject, typename TMapIterator>
488 void PdfDictionaryIndirectIterableBase<TObject, TMapIterator>::Iterator::resolve()
489 {
490  TObject& robj = m_iterator->second;
491  TObject* indirectobj;
492  PdfReference ref;
493  if (m_objects != nullptr
494  && robj.TryGetReference(ref)
495  && ref.IsIndirect()
496  && (indirectobj = GetObject(*m_objects, ref)) != nullptr)
497  {
498  m_pair = value_type(m_iterator->first, indirectobj);
499  }
500  else
501  {
502  m_pair = value_type(m_iterator->first, &robj);
503  }
504 }
505 
506 }
507 
508 #endif // PDF_DICTIONARY_H
SPDX-FileCopyrightText: (C) 2005 Dominik Seichter domseichter@web.de SPDX-FileCopyrightText: (C) 2020...
A PdfDataProvider object with a PdfObject owner, specialized in holding objects.
Definition: PdfDataContainer.h:22
Helper class to iterate through indirect objects.
Definition: PdfDictionary.h:22
The PDF dictionary data type of PoDoFo (inherits from PdfDataContainer, the base class for such repre...
Definition: PdfDictionary.h:82
const PdfObject & MustGetKey(const std::string_view &key) const
Get the key's value out of the dictionary.
const PdfObject * GetKey(const std::string_view &key) const
Get the key's value out of the dictionary.
const PdfObject * FindKeyParent(const std::string_view &key) const
Get the keys value out of the dictionary.
PdfObject * GetKey(const std::string_view &key)
Get the key's value out of the dictionary.
const PdfObject * FindKey(const std::string_view &key) const
Get the keys value out of the dictionary.
A list of PdfObjects that constitutes the indirect object list of the document The PdfParser will rea...
Definition: PdfIndirectObjectList.h:30
This class represents a PdfName.
Definition: PdfName.h:24
A PDF stream can be appended to any PdfObject and can contain arbitrary data.
Definition: PdfObjectStream.h:87
This class represents a PDF indirect Object in memory.
Definition: PdfObject.h:35
A simple tokenizer for PDF files and PDF content streams.
Definition: PdfTokenizer.h:53
SPDX-FileCopyrightText: (C) 2022 Francesco Pretto ceztko@gmail.com SPDX-License-Identifier: LGPL-2....
Definition: basetypes.h:16
PdfWriteFlags
Specify additional options for writing the PDF.
Definition: PdfDeclarations.h:137