1// -*- c-basic-offset: 4; indent-tabs-mode:nil -*-
2// vim: set ts=4 sts=4 sw=4 et:
3/* This file is part of the KDE libraries
4 Copyright (C) 2000-2005 David Faure <faure@kde.org>
5
6 This library is free software; you can redistribute it and/or
7 modify it under the terms of the GNU Library General Public
8 License version 2 as published by the Free Software Foundation.
9
10 This library is distributed in the hope that it will be useful,
11 but WITHOUT ANY WARRANTY; without even the implied warranty of
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13 Library General Public License for more details.
14
15 You should have received a copy of the GNU Library General Public License
16 along with this library; see the file COPYING.LIB. If not, write to
17 the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
18 Boston, MA 02110-1301, USA.
19*/
20#ifndef __kbookmark_h
21#define __kbookmark_h
22
23#include <kio/kio_export.h>
24
25#include <QtCore/QString>
26#include <QtCore/QList>
27#include <QtCore/QMetaType>
28#include <QtXml/QDomElement>
29#include <kurl.h>
30
31class KBookmarkManager;
32class KBookmarkGroup;
33
34class KIO_EXPORT KBookmark
35{
36 friend class KBookmarkGroup;
37public:
38 enum MetaDataOverwriteMode {
39 OverwriteMetaData, DontOverwriteMetaData
40 };
41
42 /**
43 * KUrl::Bookmark is a QList that contains bookmarks with a few
44 * convenience methods.
45 * @see KBookmark
46 * @see QList
47 */
48 class KIO_EXPORT List : public QList<KBookmark>
49 {
50 public:
51 List();
52
53 /**
54 * Adds this list of bookmark into the given QMimeData.
55 *
56 * @param mimeData the QMimeData instance used to drag or copy this bookmark
57 */
58 void populateMimeData( QMimeData* mimeData ) const;
59
60 /**
61 * Return true if @p mimeData contains bookmarks
62 */
63 static bool canDecode( const QMimeData *mimeData );
64
65 /**
66 * Return the list of mimeTypes that can be decoded by fromMimeData
67 */
68 static QStringList mimeDataTypes();
69
70 /**
71 * Extract a list of bookmarks from the contents of @p mimeData.
72 * Decoding will fail if @p mimeData does not contain any bookmarks.
73 * @param mimeData the mime data to extract from; cannot be 0
74 * @return the list of bookmarks
75 * @note those bookmarks are valid QDomElements, but their parent QDomDocument
76 * is already deleted, do not use ownerDocument()
77 * @deprecated use fromMimeData(mimeData, doc), to avoid crashes
78 */
79#ifndef KDE_NO_DEPRECATED
80 static KDE_DEPRECATED KBookmark::List fromMimeData( const QMimeData *mimeData );
81#endif
82
83 /**
84 * Extract a list of bookmarks from the contents of @p mimeData.
85 * Decoding will fail if @p mimeData does not contain any bookmarks.
86 * @param mimeData the mime data to extract from; cannot be 0
87 * @param parentDocument pass an empty QDomDocument here, it will be used as
88 * container for the bookmarks. You just need to make sure it stays alive longer
89 * (or just as long) as the returned bookmarks.
90 * @return the list of bookmarks
91 * @since 4.3.2
92 */
93 static KBookmark::List fromMimeData( const QMimeData *mimeData, QDomDocument& parentDocument );
94 };
95
96
97 /**
98 * Constructs a null bookmark, i.e. a bookmark for which isNull() returns true
99 * If you want to create a new bookmark use eitehr KBookmarkGroup.addBookmark
100 * or if you want an interactive dialog use KBookmarkDialog.
101 */
102 KBookmark( );
103
104 /**
105 * Creates the KBookmark wrapper for @param elem
106 * Mostly for internal usage.
107 */
108
109 explicit KBookmark( const QDomElement &elem );
110
111 /**
112 * Creates a stand alone bookmark. This is fairly expensive since a new QDom Tree is build.
113 */
114 static KBookmark standaloneBookmark( const QString & text, const KUrl & url, const QString & icon = QString() );
115
116 /**
117 * Whether the bookmark is a group or a normal bookmark
118 */
119 bool isGroup() const;
120
121 /**
122 * Whether the bookmark is a separator
123 */
124 bool isSeparator() const;
125
126 /**
127 * @return true if this is a null bookmark. This will never
128 * be the case for a real bookmark (in a menu), but it's used
129 * for instance as the end condition for KBookmarkGroup::next()
130 */
131 bool isNull() const;
132
133 /**
134 * @return true if bookmark is contained by a QDomDocument,
135 * if not it is most likely that it has become separated and
136 * is thus invalid and/or has been deleted from the bookmarks.
137 */
138 bool hasParent() const;
139
140 /**
141 * Text shown for the bookmark
142 * If bigger than 40, the text is shortened by
143 * replacing middle characters with "..." (see KStringHandler::csqueeze)
144 */
145 QString text() const;
146 /**
147 * Text shown for the bookmark, not truncated.
148 * You should not use this - this is mainly for keditbookmarks.
149 */
150 QString fullText() const;
151 /**
152 * Set the text shown for the bookmark.
153 *
154 * @param fullText the new bookmark title
155 */
156 void setFullText(const QString &fullText);
157 /**
158 * URL contained by the bookmark
159 */
160 KUrl url() const;
161 /**
162 * Set the URL of the bookmark
163 *
164 * @param url the new bookmark URL
165 */
166 void setUrl(const KUrl &url);
167
168 /**
169 * @return the pixmap file for this bookmark
170 * (i.e. the name of the icon)
171 */
172 QString icon() const;
173
174 /**
175 * Set the icon name of the bookmark
176 *
177 * @param icon the new icon name for this bookmark
178 */
179 void setIcon(const QString &icon);
180
181 /**
182 * @return Description of the bookmark
183 * @since 4.4
184 */
185 QString description() const;
186
187 /**
188 * Set the description of the bookmark
189 *
190 * @param description
191 * @since 4.4
192 */
193 void setDescription(const QString &description);
194
195 /**
196 * @return Mime-Type of this item
197 * @since 4.1
198 */
199 QString mimeType() const;
200
201 /**
202 * Set the Mime-Type of this item
203 *
204 * @param Mime-Type
205 * @since 4.1
206 */
207 void setMimeType(const QString &mimeType);
208
209 /**
210 * @return if the bookmark should be shown in the toolbar
211 * (used by the filtered toolbar)
212 *
213 */
214 bool showInToolbar() const;
215
216 /**
217 * Set whether this bookmark is show in a filterd toolbar
218 */
219 void setShowInToolbar(bool show);
220
221
222 /**
223 * @return the group containing this bookmark
224 */
225 KBookmarkGroup parentGroup() const;
226
227 /**
228 * Convert this to a group - do this only if
229 * isGroup() returns true.
230 */
231 KBookmarkGroup toGroup() const;
232
233 /**
234 * Return the "address" of this bookmark in the whole tree.
235 * This is used when telling other processes about a change
236 * in a given bookmark. The encoding of the address is "/4/2", for
237 * instance, to designate the 2nd child inside the 4th child of the
238 * root bookmark.
239 */
240 QString address() const;
241
242 /**
243 * Return the position in the parent, i.e. the last number in the address
244 */
245 int positionInParent() const;
246
247 // Hard to decide. Good design would imply that each bookmark
248 // knows about its manager, so that there can be several managers.
249 // But if we say there is only one manager (i.e. set of bookmarks)
250 // per application, then KBookmarkManager::self() is much easier.
251 //KBookmarkManager * manager() const { return m_manager; }
252
253 /**
254 * @internal for KEditBookmarks
255 */
256 QDomElement internalElement() const;
257
258 /**
259 * Updates the bookmarks access metadata
260 * Call when a user accesses the bookmark
261 */
262 void updateAccessMetadata();
263
264 // Utility functions (internal)
265
266 /**
267 * @return address of parent
268 */
269 static QString parentAddress( const QString & address );
270
271 /**
272 * @return position in parent (e.g. /4/5/2 -> 2)
273 */
274 static uint positionInParent( const QString & address );
275
276 /**
277 * @return address of previous sibling (e.g. /4/5/2 -> /4/5/1)
278 * Returns QString() for a first child
279 */
280 static QString previousAddress( const QString & address );
281
282 /**
283 * @return address of next sibling (e.g. /4/5/2 -> /4/5/3)
284 * This doesn't check whether it actually exists
285 */
286 static QString nextAddress( const QString & address );
287
288 /**
289 * @return the common parent of both addresses which
290 * has the greatest depth
291 */
292 static QString commonParent( const QString &A, const QString &B );
293
294 /**
295 * @return the metadata container node for a certain matadata owner
296 * @since 4.1
297 */
298 QDomNode metaData(const QString &owner, bool create) const;
299
300 /**
301 * Get the value of a specific metadata item (owner = "http://www.kde.org").
302 * @param key Name of the metadata item
303 * @return Value of the metadata item. QString() is returned in case
304 * the specified key does not exist.
305 */
306 QString metaDataItem( const QString &key ) const;
307
308 /**
309 * Change the value of a specific metadata item, or create the given item
310 * if it doesn't exist already (owner = "http://www.kde.org").
311 * @param key Name of the metadata item to change
312 * @param value Value to use for the specified metadata item
313 * @param mode Whether to overwrite the item's value if it exists already or not.
314 */
315 void setMetaDataItem( const QString &key, const QString &value, MetaDataOverwriteMode mode = OverwriteMetaData );
316
317 /**
318 * Adds this bookmark into the given QMimeData.
319 *
320 * WARNING: do not call this method multiple times, use KBookmark::List::populateMimeData instead.
321 *
322 * @param mimeData the QMimeData instance used to drag or copy this bookmark
323 */
324 void populateMimeData( QMimeData* mimeData ) const;
325
326 /**
327 * Comparison operator
328 */
329 bool operator==(const KBookmark& rhs) const;
330
331protected:
332 QDomElement element;
333 // Note: you can't add new member variables here.
334 // The KBookmarks are created on the fly, as wrappers
335 // around internal QDomElements. Any additional information
336 // has to be implemented as an attribute of the QDomElement.
337
338};
339
340#ifdef MAKE_KIO_LIB
341KDE_DUMMY_QHASH_FUNCTION(KBookmark)
342#endif
343
344/**
345 * A group of bookmarks
346 */
347class KIO_EXPORT KBookmarkGroup : public KBookmark
348{
349public:
350 /**
351 * Create an invalid group. This is mostly for use in QValueList,
352 * and other places where we need a null group.
353 * Also used as a parent for a bookmark that doesn't have one
354 * (e.g. Netscape bookmarks)
355 */
356 KBookmarkGroup();
357
358 /**
359 * Create a bookmark group as specified by the given element
360 */
361 KBookmarkGroup( const QDomElement &elem );
362
363 /**
364 * @return true if the bookmark folder is opened in the bookmark editor
365 */
366 bool isOpen() const;
367
368 /**
369 * Return the first child bookmark of this group
370 */
371 KBookmark first() const;
372 /**
373 * Return the prevous sibling of a child bookmark of this group
374 * @param current has to be one of our child bookmarks.
375 */
376 KBookmark previous( const KBookmark & current ) const;
377 /**
378 * Return the next sibling of a child bookmark of this group
379 * @param current has to be one of our child bookmarks.
380 */
381 KBookmark next( const KBookmark & current ) const;
382
383 /**
384 * Return the index of a child bookmark, -1 if not found
385 */
386 int indexOf(const KBookmark& child) const;
387
388 /**
389 * Create a new bookmark folder, as the last child of this group
390 * @param text for the folder.
391 * If you want an dialog use KBookmarkDialog
392 */
393 KBookmarkGroup createNewFolder( const QString & text );
394 /**
395 * Create a new bookmark separator
396 * Don't forget to use KBookmarkManager::self()->emitChanged( parentBookmark );
397 */
398 KBookmark createNewSeparator();
399
400 /**
401 * Create a new bookmark, as the last child of this group
402 * Don't forget to use KBookmarkManager::self()->emitChanged( parentBookmark );
403 * @param bm the bookmark to add
404 */
405 KBookmark addBookmark( const KBookmark &bm );
406
407 /**
408 * Create a new bookmark, as the last child of this group
409 * Don't forget to use KBookmarkManager::self()->emitChanged( parentBookmark );
410 * @param text for the bookmark
411 * @param url the URL that the bookmark points to
412 * @param icon the name of the icon to associate with the bookmark. A suitable default
413 * will be determined from the URL if not specified.
414 */
415 KBookmark addBookmark( const QString & text, const KUrl & url, const QString & icon = QString() );
416
417 /**
418 * Moves @p bookmark after @p after (which should be a child of ours).
419 * If after is null, @p bookmark is moved as the first child.
420 * Don't forget to use KBookmarkManager::self()->emitChanged( parentBookmark );
421 */
422 bool moveBookmark( const KBookmark & bookmark, const KBookmark & after);
423
424#ifndef KDE_NO_DEPRECATED
425 KDE_DEPRECATED bool moveItem( const KBookmark & item, const KBookmark & after );
426#endif
427
428 /**
429 * Delete a bookmark - it has to be one of our children !
430 * Don't forget to use KBookmarkManager::self()->emitChanged( parentBookmark );
431 */
432 void deleteBookmark( const KBookmark &bk );
433
434 /**
435 * @return true if this is the toolbar group
436 */
437 bool isToolbarGroup() const;
438 /**
439 * @internal
440 */
441 QDomElement findToolbar() const;
442
443 /**
444 * @return the list of urls of bookmarks at top level of the group
445 */
446 QList<KUrl> groupUrlList() const;
447
448protected:
449 QDomElement nextKnownTag( const QDomElement &start, bool goNext ) const;
450
451private:
452
453 // Note: you can't add other member variables here, except for caching info.
454 // The KBookmarks are created on the fly, as wrappers
455 // around internal QDomElements. Any additional information
456 // has to be implemented as an attribute of the QDomElement.
457};
458
459class KIO_EXPORT KBookmarkGroupTraverser {
460protected:
461 virtual ~KBookmarkGroupTraverser();
462 void traverse(const KBookmarkGroup &);
463 virtual void visit(const KBookmark &);
464 virtual void visitEnter(const KBookmarkGroup &);
465 virtual void visitLeave(const KBookmarkGroup &);
466};
467
468#define KIO_KBOOKMARK_METATYPE_DEFINED 1
469Q_DECLARE_METATYPE( KBookmark )
470
471#endif
472