demos/browser/xbel.cpp
changeset 0 1918ee327afb
child 4 3b1da2848fc7
equal deleted inserted replaced
-1:000000000000 0:1918ee327afb
       
     1 /****************************************************************************
       
     2 **
       
     3 ** Copyright (C) 2009 Nokia Corporation and/or its subsidiary(-ies).
       
     4 ** All rights reserved.
       
     5 ** Contact: Nokia Corporation (qt-info@nokia.com)
       
     6 **
       
     7 ** This file is part of the demonstration applications of the Qt Toolkit.
       
     8 **
       
     9 ** $QT_BEGIN_LICENSE:LGPL$
       
    10 ** No Commercial Usage
       
    11 ** This file contains pre-release code and may not be distributed.
       
    12 ** You may use this file in accordance with the terms and conditions
       
    13 ** contained in the Technology Preview License Agreement accompanying
       
    14 ** this package.
       
    15 **
       
    16 ** GNU Lesser General Public License Usage
       
    17 ** Alternatively, this file may be used under the terms of the GNU Lesser
       
    18 ** General Public License version 2.1 as published by the Free Software
       
    19 ** Foundation and appearing in the file LICENSE.LGPL included in the
       
    20 ** packaging of this file.  Please review the following information to
       
    21 ** ensure the GNU Lesser General Public License version 2.1 requirements
       
    22 ** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
       
    23 **
       
    24 ** In addition, as a special exception, Nokia gives you certain additional
       
    25 ** rights.  These rights are described in the Nokia Qt LGPL Exception
       
    26 ** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
       
    27 **
       
    28 ** If you have questions regarding the use of this file, please contact
       
    29 ** Nokia at qt-info@nokia.com.
       
    30 **
       
    31 **
       
    32 **
       
    33 **
       
    34 **
       
    35 **
       
    36 **
       
    37 **
       
    38 ** $QT_END_LICENSE$
       
    39 **
       
    40 ****************************************************************************/
       
    41 
       
    42 #include "xbel.h"
       
    43 
       
    44 #include <QtCore/QFile>
       
    45 
       
    46 BookmarkNode::BookmarkNode(BookmarkNode::Type type, BookmarkNode *parent) :
       
    47      expanded(false)
       
    48    , m_parent(parent)
       
    49    , m_type(type)
       
    50 {
       
    51     if (parent)
       
    52         parent->add(this);
       
    53 }
       
    54 
       
    55 BookmarkNode::~BookmarkNode()
       
    56 {
       
    57     if (m_parent)
       
    58         m_parent->remove(this);
       
    59     qDeleteAll(m_children);
       
    60     m_parent = 0;
       
    61     m_type = BookmarkNode::Root;
       
    62 }
       
    63 
       
    64 bool BookmarkNode::operator==(const BookmarkNode &other)
       
    65 {
       
    66     if (url != other.url
       
    67         || title != other.title
       
    68         || desc != other.desc
       
    69         || expanded != other.expanded
       
    70         || m_type != other.m_type
       
    71         || m_children.count() != other.m_children.count())
       
    72         return false;
       
    73 
       
    74     for (int i = 0; i < m_children.count(); ++i)
       
    75         if (!((*(m_children[i])) == (*(other.m_children[i]))))
       
    76             return false;
       
    77     return true;
       
    78 }
       
    79 
       
    80 BookmarkNode::Type BookmarkNode::type() const
       
    81 {
       
    82     return m_type;
       
    83 }
       
    84 
       
    85 void BookmarkNode::setType(Type type)
       
    86 {
       
    87     m_type = type;
       
    88 }
       
    89 
       
    90 QList<BookmarkNode *> BookmarkNode::children() const
       
    91 {
       
    92     return m_children;
       
    93 }
       
    94 
       
    95 BookmarkNode *BookmarkNode::parent() const
       
    96 {
       
    97     return m_parent;
       
    98 }
       
    99 
       
   100 void BookmarkNode::add(BookmarkNode *child, int offset)
       
   101 {
       
   102     Q_ASSERT(child->m_type != Root);
       
   103     if (child->m_parent)
       
   104         child->m_parent->remove(child);
       
   105     child->m_parent = this;
       
   106     if (-1 == offset)
       
   107         offset = m_children.size();
       
   108     m_children.insert(offset, child);
       
   109 }
       
   110 
       
   111 void BookmarkNode::remove(BookmarkNode *child)
       
   112 {
       
   113     child->m_parent = 0;
       
   114     m_children.removeAll(child);
       
   115 }
       
   116 
       
   117 
       
   118 XbelReader::XbelReader()
       
   119 {
       
   120 }
       
   121 
       
   122 BookmarkNode *XbelReader::read(const QString &fileName)
       
   123 {
       
   124     QFile file(fileName);
       
   125     if (!file.exists()) {
       
   126         return new BookmarkNode(BookmarkNode::Root);
       
   127     }
       
   128     file.open(QFile::ReadOnly);
       
   129     return read(&file);
       
   130 }
       
   131 
       
   132 BookmarkNode *XbelReader::read(QIODevice *device)
       
   133 {
       
   134     BookmarkNode *root = new BookmarkNode(BookmarkNode::Root);
       
   135     setDevice(device);
       
   136     if (readNextStartElement()) {
       
   137         QString version = attributes().value(QLatin1String("version")).toString();
       
   138         if (name() == QLatin1String("xbel")
       
   139             && (version.isEmpty() || version == QLatin1String("1.0"))) {
       
   140             readXBEL(root);
       
   141         } else {
       
   142             raiseError(QObject::tr("The file is not an XBEL version 1.0 file."));
       
   143         }
       
   144     }
       
   145     return root;
       
   146 }
       
   147 
       
   148 void XbelReader::readXBEL(BookmarkNode *parent)
       
   149 {
       
   150     Q_ASSERT(isStartElement() && name() == QLatin1String("xbel"));
       
   151 
       
   152     while (readNextStartElement()) {
       
   153         if (name() == QLatin1String("folder"))
       
   154             readFolder(parent);
       
   155         else if (name() == QLatin1String("bookmark"))
       
   156             readBookmarkNode(parent);
       
   157         else if (name() == QLatin1String("separator"))
       
   158             readSeparator(parent);
       
   159         else
       
   160             skipCurrentElement();
       
   161     }
       
   162 }
       
   163 
       
   164 void XbelReader::readFolder(BookmarkNode *parent)
       
   165 {
       
   166     Q_ASSERT(isStartElement() && name() == QLatin1String("folder"));
       
   167 
       
   168     BookmarkNode *folder = new BookmarkNode(BookmarkNode::Folder, parent);
       
   169     folder->expanded = (attributes().value(QLatin1String("folded")) == QLatin1String("no"));
       
   170 
       
   171     while (readNextStartElement()) {
       
   172         if (name() == QLatin1String("title"))
       
   173             readTitle(folder);
       
   174         else if (name() == QLatin1String("desc"))
       
   175             readDescription(folder);
       
   176         else if (name() == QLatin1String("folder"))
       
   177             readFolder(folder);
       
   178         else if (name() == QLatin1String("bookmark"))
       
   179             readBookmarkNode(folder);
       
   180         else if (name() == QLatin1String("separator"))
       
   181             readSeparator(folder);
       
   182         else
       
   183             skipCurrentElement();
       
   184     }
       
   185 }
       
   186 
       
   187 void XbelReader::readTitle(BookmarkNode *parent)
       
   188 {
       
   189     Q_ASSERT(isStartElement() && name() == QLatin1String("title"));
       
   190     parent->title = readElementText();
       
   191 }
       
   192 
       
   193 void XbelReader::readDescription(BookmarkNode *parent)
       
   194 {
       
   195     Q_ASSERT(isStartElement() && name() == QLatin1String("desc"));
       
   196     parent->desc = readElementText();
       
   197 }
       
   198 
       
   199 void XbelReader::readSeparator(BookmarkNode *parent)
       
   200 {
       
   201     new BookmarkNode(BookmarkNode::Separator, parent);
       
   202     // empty elements have a start and end element
       
   203     readNext();
       
   204 }
       
   205 
       
   206 void XbelReader::readBookmarkNode(BookmarkNode *parent)
       
   207 {
       
   208     Q_ASSERT(isStartElement() && name() == QLatin1String("bookmark"));
       
   209     BookmarkNode *bookmark = new BookmarkNode(BookmarkNode::Bookmark, parent);
       
   210     bookmark->url = attributes().value(QLatin1String("href")).toString();
       
   211     while (readNextStartElement()) {
       
   212         if (name() == QLatin1String("title"))
       
   213             readTitle(bookmark);
       
   214         else if (name() == QLatin1String("desc"))
       
   215             readDescription(bookmark);
       
   216         else
       
   217             skipCurrentElement();
       
   218     }
       
   219     if (bookmark->title.isEmpty())
       
   220         bookmark->title = QObject::tr("Unknown title");
       
   221 }
       
   222 
       
   223 
       
   224 XbelWriter::XbelWriter()
       
   225 {
       
   226     setAutoFormatting(true);
       
   227 }
       
   228 
       
   229 bool XbelWriter::write(const QString &fileName, const BookmarkNode *root)
       
   230 {
       
   231     QFile file(fileName);
       
   232     if (!root || !file.open(QFile::WriteOnly))
       
   233         return false;
       
   234     return write(&file, root);
       
   235 }
       
   236 
       
   237 bool XbelWriter::write(QIODevice *device, const BookmarkNode *root)
       
   238 {
       
   239     setDevice(device);
       
   240 
       
   241     writeStartDocument();
       
   242     writeDTD(QLatin1String("<!DOCTYPE xbel>"));
       
   243     writeStartElement(QLatin1String("xbel"));
       
   244     writeAttribute(QLatin1String("version"), QLatin1String("1.0"));
       
   245     if (root->type() == BookmarkNode::Root) {
       
   246         for (int i = 0; i < root->children().count(); ++i)
       
   247             writeItem(root->children().at(i));
       
   248     } else {
       
   249         writeItem(root);
       
   250     }
       
   251 
       
   252     writeEndDocument();
       
   253     return true;
       
   254 }
       
   255 
       
   256 void XbelWriter::writeItem(const BookmarkNode *parent)
       
   257 {
       
   258     switch (parent->type()) {
       
   259     case BookmarkNode::Folder:
       
   260         writeStartElement(QLatin1String("folder"));
       
   261         writeAttribute(QLatin1String("folded"), parent->expanded ? QLatin1String("no") : QLatin1String("yes"));
       
   262         writeTextElement(QLatin1String("title"), parent->title);
       
   263         for (int i = 0; i < parent->children().count(); ++i)
       
   264             writeItem(parent->children().at(i));
       
   265         writeEndElement();
       
   266         break;
       
   267     case BookmarkNode::Bookmark:
       
   268         writeStartElement(QLatin1String("bookmark"));
       
   269         if (!parent->url.isEmpty())
       
   270             writeAttribute(QLatin1String("href"), parent->url);
       
   271         writeTextElement(QLatin1String("title"), parent->title);
       
   272         if (!parent->desc.isEmpty())
       
   273             writeAttribute(QLatin1String("desc"), parent->desc);
       
   274         writeEndElement();
       
   275         break;
       
   276     case BookmarkNode::Separator:
       
   277         writeEmptyElement(QLatin1String("separator"));
       
   278         break;
       
   279     default:
       
   280         break;
       
   281     }
       
   282 }
       
   283