1 // Copyright 2014 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.
5 // Original code copyright 2014 Foxit Software Inc. http://www.foxitsoftware.com
7 #include "../../include/fpdfdoc/fpdf_doc.h"
8 #include "../../include/fxcrt/fx_xml.h"
9 typedef struct _PDFDOC_METADATA {
10 CPDF_Document *m_pDoc;
11 CXML_Element *m_pXmlElmnt;
12 CXML_Element *m_pElmntRdf;
13 CFX_CMapByteStringToPtr *m_pStringMap;
14 } PDFDOC_METADATA, * PDFDOC_LPMETADATA;
15 typedef PDFDOC_METADATA const * PDFDOC_LPCMETADATA;
16 const FX_LPCSTR gs_FPDFDOC_Metadata_Titles[] = {
18 "Subject", "description",
20 "Keywords", "Keywords",
21 "Producer", "Producer",
22 "Creator", "CreatorTool",
23 "CreationDate", "CreateDate",
24 "ModDate", "ModifyDate",
25 "MetadataDate", "MetadataDate"
27 CPDF_Metadata::CPDF_Metadata()
29 m_pData = FX_Alloc(PDFDOC_METADATA, 1);
30 CFX_CMapByteStringToPtr *&pStringMap = ((PDFDOC_LPMETADATA)m_pData)->m_pStringMap;
31 pStringMap = FX_NEW(CFX_CMapByteStringToPtr);
32 if (pStringMap != NULL) {
34 for (int i = 0; i < 18; i += 2) {
35 bstr = gs_FPDFDOC_Metadata_Titles[i];
36 pStringMap->AddValue(bstr, (void*)gs_FPDFDOC_Metadata_Titles[i + 1]);
40 CPDF_Metadata::~CPDF_Metadata()
42 FXSYS_assert(m_pData != NULL);
43 CXML_Element *&p = ((PDFDOC_LPMETADATA)m_pData)->m_pXmlElmnt;
47 CFX_CMapByteStringToPtr *pStringMap = ((PDFDOC_LPMETADATA)m_pData)->m_pStringMap;
49 pStringMap->RemoveAll();
54 void CPDF_Metadata::LoadDoc(CPDF_Document *pDoc)
56 FXSYS_assert(pDoc != NULL);
57 ((PDFDOC_LPMETADATA)m_pData)->m_pDoc = pDoc;
58 CPDF_Dictionary *pRoot = pDoc->GetRoot();
59 CPDF_Stream *pStream = pRoot->GetStream(FX_BSTRC("Metadata"));
64 acc.LoadAllData(pStream, FALSE);
65 int size = acc.GetSize();
66 FX_LPCBYTE pBuf = acc.GetData();
67 CXML_Element *&pXmlElmnt = ((PDFDOC_LPMETADATA)m_pData)->m_pXmlElmnt;
68 pXmlElmnt = CXML_Element::Parse(pBuf, size);
72 CXML_Element *&pElmntRdf = ((PDFDOC_LPMETADATA)m_pData)->m_pElmntRdf;
73 if (pXmlElmnt->GetTagName() == FX_BSTRC("RDF")) {
74 pElmntRdf = pXmlElmnt;
76 pElmntRdf = pXmlElmnt->GetElement(NULL, FX_BSTRC("RDF"));
79 FX_INT32 CPDF_Metadata::GetString(FX_BSTR bsItem, CFX_WideString &wsStr)
81 if (!((PDFDOC_LPMETADATA)m_pData)->m_pXmlElmnt) {
84 if (!((PDFDOC_LPMETADATA)m_pData)->m_pStringMap) {
88 if (!((PDFDOC_LPMETADATA)m_pData)->m_pStringMap->Lookup(bsItem, szTag)) {
91 CFX_ByteString bsTag = (FX_LPCSTR)szTag;
93 CXML_Element *pElmntRdf = ((PDFDOC_LPMETADATA)m_pData)->m_pElmntRdf;
97 int nChild = pElmntRdf->CountChildren();
98 for (int i = 0; i < nChild; i++) {
99 CXML_Element *pTag = pElmntRdf->GetElement(NULL, FX_BSTRC("Description"), i);
103 if (bsItem == FX_BSTRC("Title") || bsItem == FX_BSTRC("Subject")) {
104 CXML_Element *pElmnt = pTag->GetElement(NULL, bsTag);
108 pElmnt = pElmnt->GetElement(NULL, FX_BSTRC("Alt"));
112 pElmnt = pElmnt->GetElement(NULL, FX_BSTRC("li"));
116 wsStr = pElmnt->GetContent(0);
117 return wsStr.GetLength();
118 } else if (bsItem == FX_BSTRC("Author")) {
119 CXML_Element *pElmnt = pTag->GetElement(NULL, bsTag);
123 pElmnt = pElmnt->GetElement(NULL, FX_BSTRC("Seq"));
127 pElmnt = pElmnt->GetElement(NULL, FX_BSTRC("li"));
131 wsStr = pElmnt->GetContent(0);
132 return wsStr.GetLength();
134 CXML_Element *pElmnt = pTag->GetElement(NULL, bsTag);
138 wsStr = pElmnt->GetContent(0);
139 return wsStr.GetLength();
144 CXML_Element* CPDF_Metadata::GetRoot() const
146 return ((PDFDOC_LPMETADATA)m_pData)->m_pXmlElmnt;
148 CXML_Element* CPDF_Metadata::GetRDF() const
150 return ((PDFDOC_LPMETADATA)m_pData)->m_pElmntRdf;