TagLib  2.2.1
ebmlelement.h
Go to the documentation of this file.
1 /***************************************************************************
2  * This library is free software; you can redistribute it and/or modify *
3  * it under the terms of the GNU Lesser General Public License version *
4  * 2.1 as published by the Free Software Foundation. *
5  * *
6  * This library is distributed in the hope that it will be useful, but *
7  * WITHOUT ANY WARRANTY; without even the implied warranty of *
8  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU *
9  * Lesser General Public License for more details. *
10  * *
11  * You should have received a copy of the GNU Lesser General Public *
12  * License along with this library; if not, write to the Free Software *
13  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA *
14  * 02110-1301 USA *
15  * *
16  * Alternatively, this file is available under the Mozilla Public *
17  * License Version 1.1. You may obtain a copy of the License at *
18  * http://www.mozilla.org/MPL/ *
19  ***************************************************************************/
20 
21 #ifndef TAGLIB_EBMLELEMENT_H
22 #define TAGLIB_EBMLELEMENT_H
23 #ifndef DO_NOT_DOCUMENT
24 
25 #include <cstdint>
26 #include <memory>
27 #include "taglib.h"
28 
29 namespace TagLib
30 {
31  class File;
32  class ByteVector;
33 
34  namespace EBML {
35 
36  class Element
37  {
38  public:
39  enum class Id : unsigned int
40  {
41  EBMLHeader = 0x1A45DFA3,
42  DocType = 0x4282,
43  DocTypeVersion = 0x4287,
44  VoidElement = 0xEC,
45  MkSegment = 0x18538067,
46  MkTags = 0x1254C367,
47  MkTag = 0x7373,
48  MkTagTargets = 0x63C0,
49  MkTagTargetTypeValue = 0x68CA,
50  MkTagTrackUID = 0x63C5,
51  MkTagEditionUID = 0x63C9,
52  MkTagChapterUID = 0x63C4,
53  MkTagAttachmentUID = 0x63C6,
54  MkSimpleTag = 0x67C8,
55  MkTagName = 0x45A3,
56  MkTagLanguage = 0x447A,
57  MkTagBinary = 0x4485,
58  MkTagString = 0x4487,
59  MkTagsTagLanguage = 0x447A,
60  MkTagsLanguageDefault = 0x4484,
61  MkAttachments = 0x1941A469,
62  MkAttachedFile = 0x61A7,
63  MkAttachedFileDescription = 0x467E,
64  MkAttachedFileName = 0x466E,
65  MkAttachedFileMediaType = 0x4660,
66  MkAttachedFileData = 0x465C,
67  MkAttachedFileUID = 0x46AE,
68  MkSeekHead = 0x114D9B74,
69  MkSeek = 0x4DBB,
70  MkSeekID = 0x53AB,
71  MkSeekPosition = 0x53AC,
72  MkCluster = 0x1F43B675,
73  MkCodecState = 0xA4,
74  MkCues = 0x1C53BB6B,
75  MkCuePoint = 0xBB,
76  MkCueTime = 0xB3,
77  MkCueTrackPositions = 0xB7,
78  MkCueTrack = 0xF7,
79  MkCueClusterPosition = 0xF1,
80  MkCueRelativePosition = 0xF0,
81  MkCueDuration = 0xB2,
82  MkCueBlockNumber = 0x5378,
83  MkCueCodecState = 0xEA,
84  MkCueReference = 0xDB,
85  MkCueRefTime = 0x96,
86  MkInfo = 0x1549A966,
87  MkTimestampScale = 0x2AD7B1,
88  MkDuration = 0x4489,
89  MkTitle = 0x7BA9,
90  MkTracks = 0x1654AE6B,
91  MkTrackEntry = 0xAE,
92  MkCodecID = 0x86,
93  MkAudio = 0xE1,
94  MkSamplingFrequency = 0xB5,
95  MkBitDepth = 0x6264,
96  MkChannels = 0x9F,
97  MkChapters = 0x1043A770,
98  MkEditionEntry = 0x45B9,
99  MkEditionUID = 0x45BC,
100  MkEditionFlagDefault = 0x45DB,
101  MkEditionFlagOrdered = 0x45DD,
102  MkChapterAtom = 0xB6,
103  MkChapterUID = 0x73C4,
104  MkChapterTimeStart = 0x91,
105  MkChapterTimeEnd = 0x92,
106  MkChapterFlagHidden = 0x98,
107  MkChapterDisplay = 0x80,
108  MkChapString = 0x85,
109  MkChapLanguage = 0x437C,
110  };
111 
112  Element(Id id, int sizeLength, offset_t dataSize);
113  Element(Id id, int sizeLength, offset_t dataSize, offset_t);
114  virtual ~Element();
115 
116  virtual bool read(File &file);
117  void skipData(File &file);
118  Id getId() const;
119  offset_t headSize() const;
120  offset_t getSize() const;
121  int getSizeLength() const;
122  int64_t getDataSize() const;
123  ByteVector renderId() const;
124  virtual ByteVector render();
125  static std::unique_ptr<Element> factory(File &file);
126  static unsigned int readId(File &file);
127 
128  protected:
129  Id id;
130  int sizeLength;
131  offset_t dataSize;
132  };
133 
134  // Template specializations to ensure that elements for the different IDs
135  // are consistently created and cast. They provide a mapping between IDs
136  // and Element subclasses. The switch in factory() makes sure that the
137  // template for all IDs are instantiated, i.e. that every ID has its Element
138  // subclass mapped.
139  class MasterElement;
140  class UIntElement;
141  class BinaryElement;
142  class FloatElement;
143  class MkSegment;
144  class MkInfo;
145  class MkTracks;
146  class MkTags;
147  class MkAttachments;
148  class MkSeekHead;
149  class MkChapters;
150  class MkCues;
151  class VoidElement;
152  class UTF8StringElement;
153  class Latin1StringElement;
154 
155  template <Element::Id ID>
156  struct GetElementTypeById;
157 
158  template <> struct GetElementTypeById<Element::Id::EBMLHeader> { using type = MasterElement; };
159  template <> struct GetElementTypeById<Element::Id::DocType> { using type = Latin1StringElement; };
160  template <> struct GetElementTypeById<Element::Id::DocTypeVersion> { using type = UIntElement; };
161  template <> struct GetElementTypeById<Element::Id::MkSegment> { using type = MkSegment; };
162  template <> struct GetElementTypeById<Element::Id::MkInfo> { using type = MkInfo; };
163  template <> struct GetElementTypeById<Element::Id::MkTracks> { using type = MkTracks; };
164  template <> struct GetElementTypeById<Element::Id::MkTags> { using type = MkTags; };
165  template <> struct GetElementTypeById<Element::Id::MkAttachments> { using type = MkAttachments; };
166  template <> struct GetElementTypeById<Element::Id::MkTag> { using type = MasterElement; };
167  template <> struct GetElementTypeById<Element::Id::MkTagTargets> { using type = MasterElement; };
168  template <> struct GetElementTypeById<Element::Id::MkSimpleTag> { using type = MasterElement; };
169  template <> struct GetElementTypeById<Element::Id::MkAttachedFile> { using type = MasterElement; };
170  template <> struct GetElementTypeById<Element::Id::MkSeek> { using type = MasterElement; };
171  template <> struct GetElementTypeById<Element::Id::MkTrackEntry> { using type = MasterElement; };
172  template <> struct GetElementTypeById<Element::Id::MkAudio> { using type = MasterElement; };
173  template <> struct GetElementTypeById<Element::Id::MkCuePoint> { using type = MasterElement; };
174  template <> struct GetElementTypeById<Element::Id::MkCueTrackPositions> { using type = MasterElement; };
175  template <> struct GetElementTypeById<Element::Id::MkCueReference> { using type = MasterElement; };
176  template <> struct GetElementTypeById<Element::Id::MkCluster> { using type = MasterElement; };
177  template <> struct GetElementTypeById<Element::Id::MkCues> { using type = MkCues; };
178  template <> struct GetElementTypeById<Element::Id::MkTagName> { using type = UTF8StringElement; };
179  template <> struct GetElementTypeById<Element::Id::MkTagString> { using type = UTF8StringElement; };
180  template <> struct GetElementTypeById<Element::Id::MkAttachedFileName> { using type = UTF8StringElement; };
181  template <> struct GetElementTypeById<Element::Id::MkAttachedFileDescription> { using type = UTF8StringElement; };
182  template <> struct GetElementTypeById<Element::Id::MkTagLanguage> { using type = Latin1StringElement; };
183  template <> struct GetElementTypeById<Element::Id::MkAttachedFileMediaType> { using type = Latin1StringElement; };
184  template <> struct GetElementTypeById<Element::Id::MkCodecID> { using type = Latin1StringElement; };
185  template <> struct GetElementTypeById<Element::Id::MkTagTargetTypeValue> { using type = UIntElement; };
186  template <> struct GetElementTypeById<Element::Id::MkTagTrackUID> { using type = UIntElement; };
187  template <> struct GetElementTypeById<Element::Id::MkTagEditionUID> { using type = UIntElement; };
188  template <> struct GetElementTypeById<Element::Id::MkTagChapterUID> { using type = UIntElement; };
189  template <> struct GetElementTypeById<Element::Id::MkTagAttachmentUID> { using type = UIntElement; };
190  template <> struct GetElementTypeById<Element::Id::MkAttachedFileUID> { using type = UIntElement; };
191  template <> struct GetElementTypeById<Element::Id::MkSeekPosition> { using type = UIntElement; };
192  template <> struct GetElementTypeById<Element::Id::MkTimestampScale> { using type = UIntElement; };
193  template <> struct GetElementTypeById<Element::Id::MkBitDepth> { using type = UIntElement; };
194  template <> struct GetElementTypeById<Element::Id::MkChannels> { using type = UIntElement; };
195  template <> struct GetElementTypeById<Element::Id::MkCueTime> { using type = UIntElement; };
196  template <> struct GetElementTypeById<Element::Id::MkCueTrack> { using type = UIntElement; };
197  template <> struct GetElementTypeById<Element::Id::MkCueClusterPosition> { using type = UIntElement; };
198  template <> struct GetElementTypeById<Element::Id::MkCueRelativePosition> { using type = UIntElement; };
199  template <> struct GetElementTypeById<Element::Id::MkCueDuration> { using type = UIntElement; };
200  template <> struct GetElementTypeById<Element::Id::MkCueBlockNumber> { using type = UIntElement; };
201  template <> struct GetElementTypeById<Element::Id::MkCueCodecState> { using type = UIntElement; };
202  template <> struct GetElementTypeById<Element::Id::MkCueRefTime> { using type = UIntElement; };
203  template <> struct GetElementTypeById<Element::Id::MkTagsLanguageDefault> { using type = UIntElement; };
204  template <> struct GetElementTypeById<Element::Id::MkAttachedFileData> { using type = BinaryElement; };
205  template <> struct GetElementTypeById<Element::Id::MkSeekID> { using type = BinaryElement; };
206  template <> struct GetElementTypeById<Element::Id::MkTagBinary> { using type = BinaryElement; };
207  template <> struct GetElementTypeById<Element::Id::MkCodecState> { using type = BinaryElement; };
208  template <> struct GetElementTypeById<Element::Id::MkDuration> { using type = FloatElement; };
209  template <> struct GetElementTypeById<Element::Id::MkTitle> { using type = UTF8StringElement; };
210  template <> struct GetElementTypeById<Element::Id::MkSamplingFrequency> { using type = FloatElement; };
211  template <> struct GetElementTypeById<Element::Id::MkSeekHead> { using type = MkSeekHead; };
212  template <> struct GetElementTypeById<Element::Id::MkChapters> { using type = MkChapters; };
213  template <> struct GetElementTypeById<Element::Id::MkEditionEntry> { using type = MasterElement; };
214  template <> struct GetElementTypeById<Element::Id::MkEditionUID> { using type = UIntElement; };
215  template <> struct GetElementTypeById<Element::Id::MkEditionFlagDefault> { using type = UIntElement; };
216  template <> struct GetElementTypeById<Element::Id::MkEditionFlagOrdered> { using type = UIntElement; };
217  template <> struct GetElementTypeById<Element::Id::MkChapterAtom> { using type = MasterElement; };
218  template <> struct GetElementTypeById<Element::Id::MkChapterUID> { using type = UIntElement; };
219  template <> struct GetElementTypeById<Element::Id::MkChapterTimeStart> { using type = UIntElement; };
220  template <> struct GetElementTypeById<Element::Id::MkChapterTimeEnd> { using type = UIntElement; };
221  template <> struct GetElementTypeById<Element::Id::MkChapterFlagHidden> { using type = UIntElement; };
222  template <> struct GetElementTypeById<Element::Id::MkChapterDisplay> { using type = MasterElement; };
223  template <> struct GetElementTypeById<Element::Id::MkChapString> { using type = UTF8StringElement; };
224  template <> struct GetElementTypeById<Element::Id::MkChapLanguage> { using type = Latin1StringElement; };
225  template <> struct GetElementTypeById<Element::Id::VoidElement> { using type = VoidElement; };
226 
227  template <Element::Id ID, typename T=typename GetElementTypeById<ID>::type>
228  const T *element_cast(const std::unique_ptr<Element> &ptr)
229  {
230  return static_cast<const T *>(ptr.get());
231  }
232 
233  template <Element::Id ID, typename T=typename GetElementTypeById<ID>::type>
234  std::unique_ptr<T> element_cast(std::unique_ptr<Element> &&ptr)
235  {
236  return std::unique_ptr<T>(static_cast<T *>(ptr.release()));
237  }
238 
239  template <Element::Id ID, typename T=typename GetElementTypeById<ID>::type>
240  std::unique_ptr<T> make_unique_element(Element::Id id, int sizeLength, offset_t dataSize, offset_t offset)
241  {
242  return std::make_unique<T>(id, sizeLength, dataSize, offset);
243  }
244 
245  template <Element::Id ID, typename T=typename GetElementTypeById<ID>::type>
246  std::unique_ptr<T> make_unique_element()
247  {
248  return std::make_unique<T>(ID, 0, 0, 0);
249  }
250 
251  }
252 }
253 
254 #endif
255 #endif
off_t offset_t
Definition: taglib.h:64
A namespace for all TagLib related classes and functions.
Definition: apefile.h:41