libkonq Library API Documentation

konq_historymgr.cc

00001 /* This file is part of the KDE project
00002    Copyright (C) 2000,2001 Carsten Pfeiffer <pfeiffer@kde.org>
00003 
00004    This program is free software; you can redistribute it and/or
00005    modify it under the terms of the GNU General Public
00006    License as published by the Free Software Foundation; either
00007    version 2 of the License, or (at your option) any later version.
00008 
00009    This program is distributed in the hope that it will be useful,
00010    but WITHOUT ANY WARRANTY; without even the implied warranty of
00011    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
00012     General Public License for more details.
00013 
00014    You should have received a copy of the GNU General Public License
00015    along with this program; see the file COPYING.  If not, write to
00016    the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
00017    Boston, MA 02111-1307, USA.
00018 */
00019 
00020 #include "konq_historymgr.h"
00021 
00022 #include <dcopclient.h>
00023 
00024 #include <kapplication.h>
00025 #include <kdebug.h>
00026 #include <ksavefile.h>
00027 #include <ksimpleconfig.h>
00028 #include <kstandarddirs.h>
00029 
00030 #include <zlib.h>
00031 
00032 #include "konqbookmarkmanager.h"
00033 
00034 const Q_UINT32 KonqHistoryManager::s_historyVersion = 3;
00035 
00036 KonqHistoryManager::KonqHistoryManager( QObject *parent, const char *name )
00037     : KParts::HistoryProvider( parent, name ),
00038               KonqHistoryComm( "KonqHistoryManager" )
00039 {
00040     m_updateTimer = new QTimer( this );
00041 
00042     // defaults
00043     KConfig *config = KGlobal::config();
00044     KConfigGroupSaver cs( config, "HistorySettings" );
00045     m_maxCount = config->readNumEntry( "Maximum of History entries", 500 );
00046     m_maxCount = QMAX( 1, m_maxCount );
00047     m_maxAgeDays = config->readNumEntry( "Maximum age of History entries", 90);
00048 
00049     m_history.setAutoDelete( true );
00050     m_filename = locateLocal( "data",
00051                   QString::fromLatin1("konqueror/konq_history" ));
00052 
00053     if ( !kapp->dcopClient()->isAttached() )
00054     kapp->dcopClient()->attach();
00055 
00056 
00057     // take care of the completion object
00058     m_pCompletion = new KCompletion;
00059     m_pCompletion->setOrder( KCompletion::Weighted );
00060 
00061     // and load the history
00062     loadHistory();
00063 
00064     connect( m_updateTimer, SIGNAL( timeout() ), SLOT( slotEmitUpdated() ));
00065 }
00066 
00067 
00068 KonqHistoryManager::~KonqHistoryManager()
00069 {
00070     delete m_pCompletion;
00071     clearPending();
00072 }
00073 
00074 bool KonqHistoryManager::isSenderOfBroadcast()
00075 {
00076     DCOPClient *dc = callingDcopClient();
00077     return !dc || (dc->senderId() == dc->appId());
00078 }
00079 
00080 // loads the entire history
00081 bool KonqHistoryManager::loadHistory()
00082 {
00083     clearPending();
00084     m_history.clear();
00085     m_pCompletion->clear();
00086 
00087     QFile file( m_filename );
00088     if ( !file.open( IO_ReadOnly ) ) {
00089     if ( file.exists() )
00090         kdWarning() << "Can't open " << file.name() << endl;
00091 
00092     // try to load the old completion history
00093     bool ret = loadFallback();
00094     emit loadingFinished();
00095     return ret;
00096     }
00097 
00098     QDataStream fileStream( &file );
00099     QByteArray data; // only used for version == 2
00100     // we construct the stream object now but fill in the data later.
00101     // thanks to QBA's explicit sharing this works :)
00102     QDataStream crcStream( data, IO_ReadOnly );
00103 
00104     if ( !fileStream.atEnd() ) {
00105     Q_UINT32 version;
00106         fileStream >> version;
00107 
00108         QDataStream *stream = &fileStream;
00109 
00110         bool crcChecked = false;
00111         bool crcOk = false;
00112 
00113         if ( version == 2 || version == 3) {
00114             Q_UINT32 crc;
00115             crcChecked = true;
00116             fileStream >> crc >> data;
00117             crcOk = crc32( 0, reinterpret_cast<unsigned char *>( data.data() ), data.size() ) == crc;
00118             stream = &crcStream; // pick up the right stream
00119         }
00120 
00121     if ( version == 3 )
00122     {
00123         //Use KURL marshalling for V3 format.
00124         KonqHistoryEntry::marshalURLAsStrings = false;
00125     }
00126 
00127     if ( version != 0 && version < 3 ) //Versions 1,2 (but not 0) are also valid
00128     {
00129         //Turn on backwards compatibility mode..
00130         KonqHistoryEntry::marshalURLAsStrings = true;
00131         // it doesn't make sense to save to save maxAge and maxCount  in the
00132         // binary file, this would make backups impossible (they would clear
00133         // themselves on startup, because all entries expire).
00134         // [But V1 and V2 formats did it, so we do a dummy read]
00135         Q_UINT32 dummy;
00136         *stream >> dummy;
00137         *stream >> dummy;
00138 
00139         //OK.
00140         version = 3;
00141     }
00142 
00143         if ( s_historyVersion != version || ( crcChecked && !crcOk ) ) {
00144         kdWarning() << "The history version doesn't match, aborting loading" << endl;
00145         file.close();
00146         emit loadingFinished();
00147         return false;
00148     }
00149 
00150 
00151         while ( !stream->atEnd() ) {
00152         KonqHistoryEntry *entry = new KonqHistoryEntry;
00153         Q_CHECK_PTR( entry );
00154             *stream >> *entry;
00155         // kdDebug(1203) << "## loaded entry: " << entry->url << ",  Title: " << entry->title << endl;
00156         m_history.append( entry );
00157         QString urlString2 = entry->url.prettyURL();    
00158 
00159         addToCompletion( urlString2, entry->typedURL, entry->numberOfTimesVisited );
00160 
00161         // and fill our baseclass.
00162             QString urlString = entry->url.url();
00163         KParts::HistoryProvider::insert( urlString );
00164             // DF: also insert the "pretty" version if different
00165             // This helps getting 'visited' links on websites which don't use fully-escaped urls.
00166         
00167             if ( urlString != urlString2 )
00168                 KParts::HistoryProvider::insert( urlString2 );
00169     }
00170 
00171     kdDebug(1203) << "## loaded: " << m_history.count() << " entries." << endl;
00172 
00173     m_history.sort();
00174     adjustSize();
00175     }
00176     
00177     
00178     //This is important - we need to switch to a consistent marshalling format for
00179     //communicating between different konqueror instances. Since during an upgrade
00180     //some "old" copies may still running, we use the old format for the DCOP transfers.
00181     //This doesn't make that much difference performance-wise for single entries anyway.
00182     KonqHistoryEntry::marshalURLAsStrings = true;
00183 
00184 
00185     // Theoretically, we should emit update() here, but as we only ever
00186     // load items on startup up to now, this doesn't make much sense. Same
00187     // thing for the above loadFallback().
00188     // emit KParts::HistoryProvider::update( some list );
00189 
00190 
00191 
00192     file.close();
00193     emit loadingFinished();
00194 
00195     return true;
00196 }
00197 
00198 
00199 // saves the entire history
00200 bool KonqHistoryManager::saveHistory()
00201 {
00202     KSaveFile file( m_filename );
00203     if ( file.status() != 0 ) {
00204     kdWarning() << "Can't open " << file.name() << endl;
00205     return false;
00206     }
00207 
00208     QDataStream *fileStream = file.dataStream();
00209     *fileStream << s_historyVersion;
00210 
00211     QByteArray data;
00212     QDataStream stream( data, IO_WriteOnly );
00213 
00214     //We use KURL for marshalling URLs in entries in the V3
00215     //file format
00216     KonqHistoryEntry::marshalURLAsStrings = false;
00217     QPtrListIterator<KonqHistoryEntry> it( m_history );
00218     KonqHistoryEntry *entry;
00219     while ( (entry = it.current()) ) {
00220         stream << *entry;
00221     ++it;
00222     }
00223 
00224     //For DCOP, transfer strings instead - wire compat.
00225     KonqHistoryEntry::marshalURLAsStrings = true;
00226 
00227     Q_UINT32 crc = crc32( 0, reinterpret_cast<unsigned char *>( data.data() ), data.size() );
00228     *fileStream << crc << data;
00229 
00230     file.close();
00231 
00232     return true;
00233 }
00234 
00235 
00236 void KonqHistoryManager::adjustSize()
00237 {
00238     KonqHistoryEntry *entry = m_history.getFirst();
00239 
00240     while ( m_history.count() > m_maxCount || isExpired( entry ) ) {
00241     removeFromCompletion( entry->url.prettyURL(), entry->typedURL );
00242 
00243         QString urlString = entry->url.url();
00244     KParts::HistoryProvider::remove( urlString );
00245 
00246         addToUpdateList( urlString );
00247 
00248     emit entryRemoved( m_history.getFirst() );
00249     m_history.removeFirst(); // deletes the entry
00250 
00251     entry = m_history.getFirst();
00252     }
00253 }
00254 
00255 
00256 void KonqHistoryManager::addPending( const KURL& url, const QString& typedURL,
00257                      const QString& title )
00258 {
00259     addToHistory( true, url, typedURL, title );
00260 }
00261 
00262 void KonqHistoryManager::confirmPending( const KURL& url,
00263                      const QString& typedURL,
00264                      const QString& title )
00265 {
00266     addToHistory( false, url, typedURL, title );
00267 }
00268 
00269 
00270 void KonqHistoryManager::addToHistory( bool pending, const KURL& _url,
00271                        const QString& typedURL,
00272                        const QString& title )
00273 {
00274     kdDebug(1203) << "## addToHistory: " << _url.prettyURL() << " Typed URL: " << typedURL << ", Title: " << title << endl;
00275 
00276     if ( filterOut( _url ) ) // we only want remote URLs
00277     return;
00278 
00279     // http URLs without a path will get redirected immediately to url + '/'
00280     if ( _url.path().isEmpty() && _url.protocol().startsWith("http") )
00281     return;
00282 
00283     KURL url( _url );
00284     bool hasPass = url.hasPass();
00285     url.setPass( QString::null ); // No password in the history, especially not in the completion!
00286     url.setHost( url.host().lower() ); // All host parts lower case
00287     KonqHistoryEntry entry;
00288     QString u = url.prettyURL();
00289     entry.url = url;
00290     if ( (u != typedURL) && !hasPass )
00291     entry.typedURL = typedURL;
00292 
00293     // we only keep the title if we are confirming an entry. Otherwise,
00294     // we might get bogus titles from the previous url (actually it's just
00295     // konqueror's window caption).
00296     if ( !pending && u != title )
00297     entry.title = title;
00298     entry.firstVisited = QDateTime::currentDateTime();
00299     entry.lastVisited = entry.firstVisited;
00300 
00301     // always remove from pending if available, otherwise the else branch leaks
00302     // if the map already contains an entry for this key.
00303     QMapIterator<QString,KonqHistoryEntry*> it = m_pending.find( u );
00304     if ( it != m_pending.end() ) {
00305         delete it.data();
00306         m_pending.remove( it );
00307     }
00308 
00309     if ( !pending ) {
00310     if ( it != m_pending.end() ) {
00311         // we make a pending entry official, so we just have to update
00312         // and not increment the counter. No need to care about
00313         // firstVisited, as this is not taken into account on update.
00314         entry.numberOfTimesVisited = 0;
00315     }
00316     }
00317 
00318     else {
00319     // We add a copy of the current history entry of the url to the
00320     // pending list, so that we can restore it if the user canceled.
00321     // If there is no entry for the url yet, we just store the url.
00322     KonqHistoryEntry *oldEntry = findEntry( url );
00323     m_pending.insert( u, oldEntry ?
00324                           new KonqHistoryEntry( *oldEntry ) : 0L );
00325     }
00326 
00327     // notify all konqueror instances about the entry
00328     emitAddToHistory( entry );
00329 }
00330 
00331 // interface of KParts::HistoryManager
00332 // Usually, we only record the history for non-local URLs (i.e. filterOut()
00333 // returns false). But when using the HistoryProvider interface, we record
00334 // exactly those filtered-out urls.
00335 // Moreover, we  don't get any pending/confirming entries, just one insert()
00336 void KonqHistoryManager::insert( const QString& url )
00337 {
00338     KURL u ( url );
00339     if ( !filterOut( u ) || u.protocol() == "about" ) { // remote URL
00340     return;
00341     }
00342     // Local URL -> add to history
00343     KonqHistoryEntry entry;
00344     entry.url = u;
00345     entry.firstVisited = QDateTime::currentDateTime();
00346     entry.lastVisited = entry.firstVisited;
00347     emitAddToHistory( entry );
00348 }
00349 
00350 void KonqHistoryManager::emitAddToHistory( const KonqHistoryEntry& entry )
00351 {
00352     QByteArray data;
00353     QDataStream stream( data, IO_WriteOnly );
00354     stream << entry << objId();
00355     kapp->dcopClient()->send( "konqueror*", "KonqHistoryManager",
00356                   "notifyHistoryEntry(KonqHistoryEntry, QCString)",
00357                   data );
00358 }
00359 
00360 
00361 void KonqHistoryManager::removePending( const KURL& url )
00362 {
00363     // kdDebug(1203) << "## Removing pending... " << url.prettyURL() << endl;
00364 
00365     if ( url.isLocalFile() )
00366     return;
00367 
00368     QMapIterator<QString,KonqHistoryEntry*> it = m_pending.find( url.prettyURL() );
00369     if ( it != m_pending.end() ) {
00370     KonqHistoryEntry *oldEntry = it.data(); // the old entry, may be 0L
00371     emitRemoveFromHistory( url ); // remove the current pending entry
00372 
00373     if ( oldEntry ) // we had an entry before, now use that instead
00374         emitAddToHistory( *oldEntry );
00375 
00376     delete oldEntry;
00377     m_pending.remove( it );
00378     }
00379 }
00380 
00381 // clears the pending list and makes sure the entries get deleted.
00382 void KonqHistoryManager::clearPending()
00383 {
00384     QMapIterator<QString,KonqHistoryEntry*> it = m_pending.begin();
00385     while ( it != m_pending.end() ) {
00386     delete it.data();
00387     ++it;
00388     }
00389     m_pending.clear();
00390 }
00391 
00392 void KonqHistoryManager::emitRemoveFromHistory( const KURL& url )
00393 {
00394     QByteArray data;
00395     QDataStream stream( data, IO_WriteOnly );
00396     stream << url << objId();
00397     kapp->dcopClient()->send( "konqueror*", "KonqHistoryManager",
00398                   "notifyRemove(KURL, QCString)", data );
00399 }
00400 
00401 void KonqHistoryManager::emitRemoveFromHistory( const KURL::List& urls )
00402 {
00403     QByteArray data;
00404     QDataStream stream( data, IO_WriteOnly );
00405     stream << urls << objId();
00406     kapp->dcopClient()->send( "konqueror*", "KonqHistoryManager",
00407                   "notifyRemove(KURL::List, QCString)", data );
00408 }
00409 
00410 void KonqHistoryManager::emitClear()
00411 {
00412     QByteArray data;
00413     QDataStream stream( data, IO_WriteOnly );
00414     stream << objId();
00415     kapp->dcopClient()->send( "konqueror*", "KonqHistoryManager",
00416                   "notifyClear(QCString)", data );
00417 }
00418 
00419 void KonqHistoryManager::emitSetMaxCount( Q_UINT32 count )
00420 {
00421     QByteArray data;
00422     QDataStream stream( data, IO_WriteOnly );
00423     stream << count << objId();
00424     kapp->dcopClient()->send( "konqueror*", "KonqHistoryManager",
00425                   "notifyMaxCount(Q_UINT32, QCString)", data );
00426 }
00427 
00428 void KonqHistoryManager::emitSetMaxAge( Q_UINT32 days )
00429 {
00430     QByteArray data;
00431     QDataStream stream( data, IO_WriteOnly );
00432     stream << days << objId();
00433     kapp->dcopClient()->send( "konqueror*", "KonqHistoryManager",
00434                   "notifyMaxAge(Q_UINT32, QCString)", data );
00435 }
00436 
00438 // DCOP called methods
00439 
00440 void KonqHistoryManager::notifyHistoryEntry( KonqHistoryEntry e,
00441                          QCString  )
00442 {
00443     //kdDebug(1203) << "Got new entry from Broadcast: " << e.url.prettyURL() << endl;
00444 
00445     KonqHistoryEntry *entry = findEntry( e.url );
00446     QString urlString = e.url.url();
00447 
00448     if ( !entry ) { // create a new history entry
00449     entry = new KonqHistoryEntry;
00450     entry->url = e.url;
00451     entry->firstVisited = e.firstVisited;
00452     entry->numberOfTimesVisited = 0; // will get set to 1 below
00453     m_history.append( entry );
00454     KParts::HistoryProvider::insert( urlString );
00455     }
00456 
00457     if ( !e.typedURL.isEmpty() )
00458     entry->typedURL = e.typedURL;
00459     if ( !e.title.isEmpty() )
00460     entry->title = e.title;
00461     entry->numberOfTimesVisited += e.numberOfTimesVisited;
00462     entry->lastVisited = e.lastVisited;
00463 
00464     addToCompletion( entry->url.prettyURL(), entry->typedURL );
00465 
00466     // bool pending = (e.numberOfTimesVisited != 0);
00467 
00468     adjustSize();
00469 
00470     // note, no need to do the updateBookmarkMetadata for every
00471     // history object, only need to for the broadcast sender as
00472     // the history object itself keeps the data consistant.
00473     bool updated = KonqBookmarkManager::self()->updateAccessMetadata( urlString );
00474 
00475     if ( isSenderOfBroadcast() ) {
00476     // we are the sender of the broadcast, so we save
00477     saveHistory();
00478     // note, bk save does not notify, and we don't want to!
00479     if (updated) 
00480         KonqBookmarkManager::self()->save();
00481     }
00482 
00483     addToUpdateList( urlString );
00484     emit entryAdded( entry );
00485 }
00486 
00487 void KonqHistoryManager::notifyMaxCount( Q_UINT32 count, QCString )
00488 {
00489     m_maxCount = count;
00490     clearPending();
00491     adjustSize();
00492 
00493     KConfig *config = KGlobal::config();
00494     KConfigGroupSaver cs( config, "HistorySettings" );
00495     config->writeEntry( "Maximum of History entries", m_maxCount );
00496 
00497     if ( isSenderOfBroadcast() ) { 
00498     saveHistory();
00499     config->sync();
00500     }
00501 }
00502 
00503 void KonqHistoryManager::notifyMaxAge( Q_UINT32 days, QCString  )
00504 {
00505     m_maxAgeDays = days;
00506     clearPending();
00507     adjustSize();
00508 
00509     KConfig *config = KGlobal::config();
00510     KConfigGroupSaver cs( config, "HistorySettings" );
00511     config->writeEntry( "Maximum age of History entries", m_maxAgeDays );
00512 
00513     if ( isSenderOfBroadcast() ) { 
00514     saveHistory();
00515     config->sync();
00516     }
00517 }
00518 
00519 void KonqHistoryManager::notifyClear( QCString )
00520 {
00521     clearPending();
00522     m_history.clear();
00523     m_pCompletion->clear();
00524 
00525     if ( isSenderOfBroadcast() )
00526     saveHistory();
00527 
00528     KParts::HistoryProvider::clear(); // also emits the cleared() signal
00529 }
00530 
00531 void KonqHistoryManager::notifyRemove( KURL url, QCString )
00532 {
00533     kdDebug(1203) << "#### Broadcast: remove entry:: " << url.prettyURL() << endl;
00534     
00535 
00536     KonqHistoryEntry *entry = m_history.findEntry( url );
00537     
00538     if ( entry ) { // entry is now the current item
00539     removeFromCompletion( entry->url.prettyURL(), entry->typedURL );
00540 
00541         QString urlString = entry->url.url();
00542     KParts::HistoryProvider::remove( urlString );
00543 
00544         addToUpdateList( urlString );
00545 
00546     m_history.take(); // does not delete
00547     emit entryRemoved( entry );
00548     delete entry;
00549 
00550     if ( isSenderOfBroadcast() )
00551         saveHistory();
00552     }
00553 }
00554 
00555 void KonqHistoryManager::notifyRemove( KURL::List urls, QCString )
00556 {
00557     kdDebug(1203) << "#### Broadcast: removing list!" << endl;
00558 
00559     bool doSave = false;
00560     KURL::List::Iterator it = urls.begin();
00561     while ( it != urls.end() ) {
00562     KonqHistoryEntry *entry = m_history.findEntry( *it );
00563     
00564     if ( entry ) { // entry is now the current item
00565         removeFromCompletion( entry->url.prettyURL(), entry->typedURL );
00566 
00567             QString urlString = entry->url.url();
00568         KParts::HistoryProvider::remove( urlString );
00569 
00570             addToUpdateList( urlString );
00571 
00572         m_history.take(); // does not delete
00573         emit entryRemoved( entry );
00574         delete entry;
00575         doSave = true;
00576     }
00577 
00578     ++it;
00579     }
00580 
00581     if (doSave && isSenderOfBroadcast())
00582         saveHistory();
00583 }
00584 
00585 
00586 // compatibility fallback, try to load the old completion history
00587 bool KonqHistoryManager::loadFallback()
00588 {
00589     QString file = locateLocal( "config", QString::fromLatin1("konq_history"));
00590     if ( file.isEmpty() )
00591     return false;
00592 
00593     KonqHistoryEntry *entry;
00594     KSimpleConfig config( file );
00595     config.setGroup("History");
00596     QStringList items = config.readListEntry( "CompletionItems" );
00597     QStringList::Iterator it = items.begin();
00598 
00599     while ( it != items.end() ) {
00600     entry = createFallbackEntry( *it );
00601     if ( entry ) {
00602         m_history.append( entry );
00603         addToCompletion( entry->url.prettyURL(), QString::null, entry->numberOfTimesVisited );
00604 
00605         KParts::HistoryProvider::insert( entry->url.url() );
00606     }
00607     ++it;
00608     }
00609 
00610     m_history.sort();
00611     adjustSize();
00612     saveHistory();
00613 
00614     return true;
00615 }
00616 
00617 // tries to create a small KonqHistoryEntry out of a string, where the string
00618 // looks like "http://www.bla.com/bla.html:23"
00619 // the attached :23 is the weighting from KCompletion
00620 KonqHistoryEntry * KonqHistoryManager::createFallbackEntry(const QString& item) const
00621 {
00622     // code taken from KCompletion::addItem(), adjusted to use weight = 1
00623     uint len = item.length();
00624     uint weight = 1;
00625 
00626     // find out the weighting of this item (appended to the string as ":num")
00627     int index = item.findRev(':');
00628     if ( index > 0 ) {
00629     bool ok;
00630     weight = item.mid( index + 1 ).toUInt( &ok );
00631     if ( !ok )
00632         weight = 1;
00633 
00634     len = index; // only insert until the ':'
00635     }
00636 
00637 
00638     KonqHistoryEntry *entry = 0L;
00639     KURL u( item.left( len ));
00640     if ( u.isValid() ) {
00641     entry = new KonqHistoryEntry;
00642     // that's the only entries we know about...
00643     entry->url = u;
00644     entry->numberOfTimesVisited = weight;
00645     // to make it not expire immediately...
00646     entry->lastVisited = QDateTime::currentDateTime();
00647     }
00648 
00649     return entry;
00650 }
00651 
00652 KonqHistoryEntry * KonqHistoryManager::findEntry( const KURL& url )
00653 {
00654     // small optimization (dict lookup) for items _not_ in our history
00655     if ( !KParts::HistoryProvider::contains( url.url() ) )
00656         return 0L;
00657 
00658     return m_history.findEntry( url );
00659 }
00660 
00661 bool KonqHistoryManager::filterOut( const KURL& url )
00662 {
00663     return ( url.isLocalFile() || url.host().isEmpty() );
00664 }
00665 
00666 void KonqHistoryManager::slotEmitUpdated()
00667 {
00668     emit KParts::HistoryProvider::updated( m_updateURLs );
00669     m_updateURLs.clear();
00670 }
00671 
00672 QStringList KonqHistoryManager::allURLs() const
00673 {
00674     QStringList list;
00675     KonqHistoryIterator it ( m_history );
00676     for ( ; it.current(); ++it )
00677         list.append( it.current()->url.url() );
00678     
00679     return list;
00680 }
00681 
00682 void KonqHistoryManager::addToCompletion( const QString& url, const QString& typedURL, 
00683                                           int numberOfTimesVisited )
00684 {
00685     m_pCompletion->addItem( url, numberOfTimesVisited );
00686     // typed urls have a higher priority
00687     m_pCompletion->addItem( typedURL, numberOfTimesVisited +10 );
00688 }
00689 
00690 void KonqHistoryManager::removeFromCompletion( const QString& url, const QString& typedURL )
00691 {
00692     m_pCompletion->removeItem( url );
00693     m_pCompletion->removeItem( typedURL );
00694 }
00695 
00697 
00698 
00699 KonqHistoryEntry * KonqHistoryList::findEntry( const KURL& url )
00700 {
00701     // we search backwards, probably faster to find an entry
00702     KonqHistoryEntry *entry = last();
00703     while ( entry ) {
00704     if ( entry->url == url )
00705         return entry;
00706 
00707     entry = prev();
00708     }
00709 
00710     return 0L;
00711 }
00712 
00713 // sort by lastVisited date (oldest go first)
00714 int KonqHistoryList::compareItems( QPtrCollection::Item item1,
00715                    QPtrCollection::Item item2 )
00716 {
00717     KonqHistoryEntry *entry1 = static_cast<KonqHistoryEntry *>( item1 );
00718     KonqHistoryEntry *entry2 = static_cast<KonqHistoryEntry *>( item2 );
00719 
00720     if ( entry1->lastVisited > entry2->lastVisited )
00721     return 1;
00722     else if ( entry1->lastVisited < entry2->lastVisited )
00723     return -1;
00724     else
00725     return 0;
00726 }
00727 
00728 using namespace KParts; // for IRIX
00729 
00730 #include "konq_historymgr.moc"
KDE Logo
This file is part of the documentation for libkonq Library Version 3.4.2.
Documentation copyright © 1996-2004 the KDE developers.
Generated on Wed Jun 14 19:05:21 2006 by doxygen 1.4.4 written by Dimitri van Heesch, © 1997-2003