00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
#include "kbookmark.h"
00023
#include <qvaluestack.h>
00024
#include <kdebug.h>
00025
#include <kmimetype.h>
00026
#include <kstringhandler.h>
00027
#include <kinputdialog.h>
00028
#include <kglobal.h>
00029
#include <klocale.h>
00030
#include <assert.h>
00031
#include <kapplication.h>
00032
#include <dcopclient.h>
00033
#include <kbookmarkmanager.h>
00034
00035 KBookmarkGroup::KBookmarkGroup()
00036 : KBookmark(
QDomElement() )
00037 {
00038 }
00039
00040 KBookmarkGroup::KBookmarkGroup(
QDomElement elem )
00041 : KBookmark(elem)
00042 {
00043 }
00044
00045 QString KBookmarkGroup::groupAddress()
const
00046
{
00047
if (m_address.isEmpty())
00048 m_address = address();
00049
return m_address;
00050 }
00051
00052 bool KBookmarkGroup::isOpen()
const
00053
{
00054
return element.attribute(
"folded") ==
"no";
00055 }
00056
00057 KBookmark
KBookmarkGroup::first()
const
00058
{
00059
return KBookmark( nextKnownTag( element.firstChild().toElement(),
true ) );
00060 }
00061
00062 KBookmark
KBookmarkGroup::previous(
const KBookmark & current )
const
00063
{
00064
return KBookmark( nextKnownTag( current.element.previousSibling().toElement(),
false ) );
00065 }
00066
00067 KBookmark
KBookmarkGroup::next(
const KBookmark & current )
const
00068
{
00069
return KBookmark( nextKnownTag( current.element.nextSibling().toElement(),
true ) );
00070 }
00071
00072
QDomElement KBookmarkGroup::nextKnownTag(
QDomElement start,
bool goNext )
const
00073
{
00074
static const QString & bookmark = KGlobal::staticQString(
"bookmark");
00075
static const QString & folder = KGlobal::staticQString(
"folder");
00076
static const QString & separator = KGlobal::staticQString(
"separator");
00077
QDomElement elem = start;
00078
while ( !elem.isNull() )
00079 {
00080
QString tag = elem.tagName();
00081
if (tag == folder || tag == bookmark || tag == separator)
00082
break;
00083
if (goNext)
00084 elem = elem.nextSibling().toElement();
00085
else
00086 elem = elem.previousSibling().toElement();
00087 }
00088
return elem;
00089 }
00090
00091 KBookmarkGroup KBookmarkGroup::createNewFolder(
KBookmarkManager* mgr,
const QString & text,
bool emitSignal )
00092 {
00093
QString txt( text );
00094
if ( text.isEmpty() )
00095 {
00096
bool ok;
00097
QString caption = parentGroup().fullText().isEmpty() ?
00098 i18n(
"Create New Bookmark Folder" ) :
00099 i18n(
"Create New Bookmark Folder in %1" )
00100 .arg( parentGroup().text() );
00101 txt = KInputDialog::getText( caption, i18n(
"New folder:" ),
00102 QString::null, &ok );
00103
if ( !ok )
00104
return KBookmarkGroup();
00105 }
00106
00107 Q_ASSERT(!element.isNull());
00108
QDomDocument doc = element.ownerDocument();
00109
QDomElement groupElem = doc.createElement(
"folder" );
00110 element.appendChild( groupElem );
00111
QDomElement textElem = doc.createElement(
"title" );
00112 groupElem.appendChild( textElem );
00113 textElem.appendChild( doc.createTextNode( txt ) );
00114
00115
KBookmarkGroup grp(groupElem);
00116
00117
if (emitSignal)
00118 emit mgr->
notifier().
createdNewFolder(
00119 mgr->
path(), grp.fullText(),
00120 grp.address() );
00121
00122
return grp;
00123
00124 }
00125
00126 KBookmark
KBookmarkGroup::createNewSeparator()
00127 {
00128 Q_ASSERT(!element.isNull());
00129
QDomDocument doc = element.ownerDocument();
00130 Q_ASSERT(!doc.isNull());
00131
QDomElement sepElem = doc.createElement(
"separator" );
00132 element.appendChild( sepElem );
00133
return KBookmark(sepElem);
00134 }
00135
00136 bool KBookmarkGroup::moveItem(
const KBookmark & item,
const KBookmark & after )
00137 {
00138
QDomNode n;
00139
if ( !after.isNull() )
00140 n = element.insertAfter( item.element, after.element );
00141
else
00142 {
00143
if ( element.firstChild().isNull() )
00144 n = element.insertBefore( item.element,
QDomElement() );
00145
00146
00147
QDomElement firstChild = nextKnownTag(element.firstChild().toElement(),
true);
00148
if ( !firstChild.isNull() )
00149 n = element.insertBefore( item.element, firstChild );
00150
else
00151 {
00152
00153 n = element.appendChild( item.element );
00154 }
00155 }
00156
return (!n.isNull());
00157 }
00158
00159 KBookmark
KBookmarkGroup::addBookmark(
KBookmarkManager* mgr,
const QString & text,
const KURL & url,
const QString & icon,
bool emitSignal )
00160 {
00161
00162
QDomDocument doc = element.ownerDocument();
00163
QDomElement elem = doc.createElement(
"bookmark" );
00164 element.appendChild( elem );
00165 elem.setAttribute(
"href", url.
url( 0, 106 ) );
00166
QString _icon = icon;
00167
if ( _icon.isEmpty() )
00168 _icon = KMimeType::iconForURL( url );
00169 elem.setAttribute(
"icon", _icon );
00170
00171
QDomElement textElem = doc.createElement(
"title" );
00172 elem.appendChild( textElem );
00173 textElem.appendChild( doc.createTextNode( text ) );
00174
00175 KBookmark bk(elem);
00176
00177
if (emitSignal)
00178 emit mgr->
notifier().addedBookmark(
00179 mgr->
path(), url.
url(),
00180 text, bk.address(), icon );
00181
00182
return bk;
00183 }
00184
00185 void KBookmarkGroup::deleteBookmark( KBookmark bk )
00186 {
00187 element.removeChild( bk.element );
00188 }
00189
00190 bool KBookmarkGroup::isToolbarGroup()
const
00191
{
00192
return ( element.attribute(
"toolbar") ==
"yes" );
00193 }
00194
00195
QDomElement KBookmarkGroup::findToolbar()
const
00196
{
00197
if ( element.attribute(
"toolbar") ==
"yes" )
00198
return element;
00199
QDomElement e = element.firstChild().toElement();
00200
for ( ; !e.isNull() ; e = e.nextSibling().toElement() )
00201 {
00202
00203
if ( e.tagName() ==
"folder" )
00204 {
00205
if ( e.attribute(
"toolbar") ==
"yes" )
00206
return e;
00207
else
00208 {
00209
QDomElement result =
KBookmarkGroup(e).findToolbar();
00210
if (!result.isNull())
00211
return result;
00212 }
00213 }
00214 }
00215
return QDomElement();
00216 }
00217
00218 QValueList<KURL> KBookmarkGroup::groupUrlList()
const
00219
{
00220
QValueList<KURL> urlList;
00221
for ( KBookmark bm =
first(); !bm.isNull(); bm =
next(bm) )
00222 {
00223
if ( bm.isSeparator() || bm.isGroup() )
00224
continue;
00225 urlList << bm.url();
00226 }
00227
return urlList;
00228 }
00229
00231
00232
bool KBookmark::isGroup()
const
00233
{
00234
QString tag = element.tagName();
00235
return ( tag ==
"folder"
00236 || tag ==
"xbel" );
00237 }
00238
00239
bool KBookmark::isSeparator()
const
00240
{
00241
return (element.tagName() ==
"separator");
00242 }
00243
00244
bool KBookmark::hasParent()
const
00245
{
00246
QDomElement parent = element.parentNode().toElement();
00247
return !parent.isNull();
00248 }
00249
00250
QString KBookmark::text()
const
00251
{
00252
return KStringHandler::csqueeze( fullText() );
00253 }
00254
00255
QString KBookmark::fullText()
const
00256
{
00257
if (isSeparator())
00258
return i18n(
"--- separator ---");
00259
00260
return element.namedItem(
"title").toElement().text();
00261 }
00262
00263
KURL KBookmark::url()
const
00264
{
00265
return KURL(element.attribute(
"href"), 106);
00266 }
00267
00268
QString KBookmark::icon()
const
00269
{
00270
QString icon = element.attribute(
"icon");
00271
if ( icon.isEmpty() )
00272
00273
00274
if ( isGroup() )
00275 icon =
"bookmark_folder";
00276
else
00277
if ( isSeparator() )
00278 icon =
"eraser";
00279
else
00280 icon =
KMimeType::iconForURL( url() );
00281
return icon;
00282 }
00283
00284
KBookmarkGroup KBookmark::parentGroup()
const
00285
{
00286
return KBookmarkGroup( element.parentNode().toElement() );
00287 }
00288
00289
KBookmarkGroup KBookmark::toGroup()
const
00290
{
00291 Q_ASSERT( isGroup() );
00292
return KBookmarkGroup(element);
00293 }
00294
00295
QString KBookmark::address()
const
00296
{
00297
if ( element.tagName() ==
"xbel" )
00298
return "";
00299
else
00300 {
00301
00302
if (!hasParent())
00303 {
00304 Q_ASSERT(hasParent());
00305
return "ERROR";
00306 }
00307
KBookmarkGroup group = parentGroup();
00308
QString parentAddress = group.address();
00309 uint counter = 0;
00310
00311
00312
for ( KBookmark bk = group.
first() ; !bk.isNull() ; bk = group.
next(bk), ++counter )
00313 {
00314
if ( bk.element == element )
00315
return parentAddress +
"/" + QString::number(counter);
00316 }
00317
kdWarning() <<
"KBookmark::address : this can't happen! " << parentAddress <<
endl;
00318
return "ERROR";
00319 }
00320 }
00321
00322 KBookmark KBookmark::standaloneBookmark(
const QString & text,
const KURL & url,
const QString & icon )
00323 {
00324
QDomDocument doc(
"xbel");
00325
QDomElement elem = doc.createElement(
"xbel");
00326 doc.appendChild( elem );
00327
KBookmarkGroup grp( elem );
00328 grp.
addBookmark( 0L, text, url, icon,
false );
00329
return grp.
first();
00330 }
00331
00332
static QDomNode cd_or_create(
QDomNode node,
QString name)
00333 {
00334
QDomNode subnode = node.namedItem(name);
00335
if (subnode.isNull())
00336 {
00337 subnode = node.ownerDocument().createElement(name);
00338 node.appendChild(subnode);
00339 }
00340
return subnode;
00341 }
00342
00343
static QDomText get_or_create_text(
QDomNode node)
00344 {
00345
QDomNode subnode = node.firstChild();
00346
if (subnode.isNull())
00347 {
00348 subnode = node.ownerDocument().createTextNode(
"");
00349 node.appendChild(subnode);
00350 }
00351
return subnode.toText();
00352 }
00353
00354
void KBookmark::updateAccessMetadata()
00355 {
00356
kdDebug(7043) <<
"KBookmark::updateAccessMetadata " << address() <<
" " << url().prettyURL() <<
endl;
00357
00358
QDomNode subnode = cd_or_create(internalElement(),
"info");
00359 subnode = cd_or_create(subnode,
"metadata");
00360
00361 uint timet = QDateTime::currentDateTime().toTime_t();
00362
00363
QDomNode item = cd_or_create(subnode,
"time_added");
00364
QDomText domtext = get_or_create_text(item);
00365
if (domtext.data().isEmpty())
00366 domtext.setData(QString::number(timet));
00367
00368 item = cd_or_create(subnode,
"time_visited");
00369 domtext = get_or_create_text(item);
00370 domtext.setData(QString::number(timet));
00371
00372 item = cd_or_create(subnode,
"visit_count");
00373 domtext = get_or_create_text(item);
00374
QString countStr = domtext.data();
00375
bool ok;
00376
int currentCount = countStr.toInt(&ok);
00377
if (!ok)
00378 currentCount = 0;
00379 currentCount++;
00380 domtext.setData(QString::number(currentCount));
00381
00382
00383 }
00384
00385
void KBookmarkGroupTraverser::traverse(
const KBookmarkGroup &root)
00386 {
00387
00388
QValueStack<KBookmarkGroup> stack;
00389 stack.push(root);
00390 KBookmark bk = stack.top().first();
00391
for (;;) {
00392
if (bk.isNull())
00393 {
00394
if (stack.isEmpty())
00395
return;
00396
if (stack.count() > 1)
00397 visitLeave(stack.top());
00398 bk = stack.pop();
00399 bk = stack.top().next(bk);
00400
if (bk.isNull())
00401
continue;
00402 }
00403
00404
if (bk.isGroup())
00405 {
00406
KBookmarkGroup gp = bk.toGroup();
00407 visitEnter(gp);
00408
if (!gp.
first().isNull())
00409 {
00410 stack.push(gp);
00411 bk = gp.
first();
00412
continue;
00413 }
00414
00415 visitLeave(gp);
00416 }
00417
else
00418 visit(bk);
00419
00420 bk = stack.top().next(bk);
00421 }
00422
00423
00424 }
00425