Files
core/PdfReader/Src/Outline.cpp
Ilya.Kirillov 65d72ae4ec Убраны лишние файлы. Все файлы сконвертированы в UTF8.
git-svn-id: svn://fileserver/activex/AVS/Sources/TeamlabOffice/trunk/ServerComponents@62550 954022d7-b5bf-4e40-9824-e11837661b57
2016-05-21 00:02:55 +03:00

167 lines
3.7 KiB
C++

#include "MemoryUtils.h"
#include "StringExt.h"
#include "List.h"
#include "Link.h"
#include "PDFDocEncoding.h"
#include "Outline.h"
#include "Dict.h"
namespace PdfReader
{
//-------------------------------------------------------------------------------------------------------------------------------
// Outline
//-------------------------------------------------------------------------------------------------------------------------------
Outline::Outline(Object *pOutlineObject, XRef *pXref)
{
m_pItems = NULL;
if (!pOutlineObject->IsDict())
{
return;
}
Object oFirst, oLast;
m_pItems = OutlineItem::ReadItemList(pOutlineObject->DictLookupAndCopy("First", &oFirst), pOutlineObject->DictLookupAndCopy("Last", &oLast), pXref);
oFirst.Free();
oLast.Free();
}
Outline::~Outline()
{
if (m_pItems)
{
DeleteCList(m_pItems, OutlineItem);
}
}
//-------------------------------------------------------------------------------------------------------------------------------
// OutlineItem
//-------------------------------------------------------------------------------------------------------------------------------
OutlineItem::OutlineItem(Dict *pDict, XRef *pXref)
{
m_pXref = pXref;
m_pTitle = NULL;
m_pAction = NULL;
m_pKids = NULL;
Object oDictItem;
if (pDict->Search("Title", &oDictItem)->IsString())
{
StringExt *seTitle = oDictItem.GetString();
if ((seTitle->GetAt(0) & 0xff) == 0xfe && (seTitle->GetAt(1) & 0xff) == 0xff)
{
m_nTitleLen = (seTitle->GetLength() - 2) / 2;
m_pTitle = (Unicode *)MemUtilsMallocArray(m_nTitleLen, sizeof(Unicode));
for (int nIndex = 0; nIndex < m_nTitleLen; ++nIndex)
{
m_pTitle[nIndex] = ((seTitle->GetAt(2 + 2 * nIndex) & 0xff) << 8) | (seTitle->GetAt(3 + 2 * nIndex) & 0xff);
}
}
else
{
m_nTitleLen = seTitle->GetLength();
m_pTitle = (Unicode *)MemUtilsMallocArray(m_nTitleLen, sizeof(Unicode));
for (int nIndex = 0; nIndex < m_nTitleLen; ++nIndex)
{
m_pTitle[nIndex] = c_arrPDFDocEncoding[seTitle->GetAt(nIndex) & 0xff];
}
}
}
else
{
m_nTitleLen = 0;
}
oDictItem.Free();
if (!pDict->Search("Dest", &oDictItem)->IsNull())
{
m_pAction = LinkAction::ParseDestination(&oDictItem);
}
else
{
oDictItem.Free();
if (!pDict->Search("A", &oDictItem)->IsNull())
{
m_pAction = LinkAction::ParseAction(&oDictItem);
}
}
oDictItem.Free();
pDict->SearchAndCopy("First", &m_oFirstRef);
pDict->SearchAndCopy("Last", &m_oLastRef);
pDict->SearchAndCopy("Next", &m_oNextRef);
m_bOpen = false;
if (pDict->Search("Count", &oDictItem)->IsInt())
{
if (oDictItem.GetInt() > 0)
{
m_bOpen = true;
}
}
oDictItem.Free();
}
OutlineItem::~OutlineItem()
{
Close();
if (m_pTitle)
{
MemUtilsFree(m_pTitle);
}
if (m_pAction)
{
delete m_pAction;
}
m_oFirstRef.Free();
m_oLastRef.Free();
m_oNextRef.Free();
}
CList *OutlineItem::ReadItemList(Object *pFirstItemRef, Object *pLastItemRef, XRef *pXref)
{
CList *pItems = new CList();
Object *pCurItem = pFirstItemRef;
while (pCurItem->IsRef())
{
Object oTemp;
if (!pCurItem->Fetch(pXref, &oTemp)->IsDict())
{
oTemp.Free();
break;
}
OutlineItem *pItem = new OutlineItem(oTemp.GetDict(), pXref);
oTemp.Free();
pItems->Append(pItem);
if (pCurItem->GetRef().nNum == pLastItemRef->GetRef().nNum && pCurItem->GetRef().nGen == pLastItemRef->GetRef().nGen)
{
break;
}
pCurItem = &pItem->m_oNextRef;
}
return pItems;
}
void OutlineItem::Open()
{
if (!m_pKids)
{
m_pKids = ReadItemList(&m_oFirstRef, &m_oLastRef, m_pXref);
}
}
void OutlineItem::Close()
{
if (m_pKids)
{
DeleteCList(m_pKids, OutlineItem);
m_pKids = NULL;
}
}
}