kio Library API Documentation

kurlbar.cpp

00001 /* This file is part of the KDE libraries
00002     Copyright (C) 2001,2002,2003 Carsten Pfeiffer <pfeiffer@kde.org>
00003 
00004     library is free software; you can redistribute it and/or
00005     modify it under the terms of the GNU Library General Public
00006     License as published by the Free Software Foundation, version 2.
00007 
00008     This library is distributed in the hope that it will be useful,
00009     but WITHOUT ANY WARRANTY; without even the implied warranty of
00010     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
00011     Library General Public License for more details.
00012 
00013     You should have received a copy of the GNU Library General Public License
00014     along with this library; see the file COPYING.LIB.  If not, write to
00015     the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
00016     Boston, MA 02111-1307, USA.
00017 */
00018 
00019 #include <unistd.h>
00020 
00021 #include <qapplication.h>
00022 #include <qcheckbox.h>
00023 #include <qdrawutil.h>
00024 #include <qfontmetrics.h>
00025 #include <qlabel.h>
00026 #include <qgrid.h>
00027 #include <qpainter.h>
00028 #include <qpopupmenu.h>
00029 #include <qstyle.h>
00030 #include <qvbox.h>
00031 #include <qwhatsthis.h>
00032 
00033 #include <kstandarddirs.h>
00034 #include <kdesktopfile.h>
00035 #include <kaboutdata.h>
00036 #include <kconfig.h>
00037 #include <kdebug.h>
00038 #include <kglobal.h>
00039 #include <kicondialog.h>
00040 #include <kiconloader.h>
00041 #include <kinstance.h>
00042 #include <klineedit.h>
00043 #include <klocale.h>
00044 #include <kmimetype.h>
00045 #include <kprotocolinfo.h>
00046 #include <kstringhandler.h>
00047 #include <kurldrag.h>
00048 #include <kurlrequester.h>
00049 
00050 #include "kurlbar.h"
00051 
00056 class KURLBarToolTip : public QToolTip
00057 {
00058 public:
00059     KURLBarToolTip( QListBox *view ) : QToolTip( view ), m_view( view ) {}
00060 
00061 protected:
00062     virtual void maybeTip( const QPoint& point ) {
00063         QListBoxItem *item = m_view->itemAt( point );
00064         if ( item ) {
00065             QString text = static_cast<KURLBarItem*>( item )->toolTip();
00066             if ( !text.isEmpty() )
00067                 tip( m_view->itemRect( item ), text );
00068         }
00069     }
00070 
00071 private:
00072     QListBox *m_view;
00073 };
00074 
00075 
00078 
00079 class KURLBarItem::KURLBarItemPrivate
00080 {
00081 public:
00082     KURLBarItemPrivate()
00083     {
00084         isPersistent = true;
00085     }
00086 
00087     bool isPersistent;
00088 };
00089 
00090 KURLBarItem::KURLBarItem( KURLBar *parent,
00091                           const KURL& url, bool persistent, const QString& description,
00092                           const QString& icon, KIcon::Group group )
00093     : QListBoxPixmap( KIconLoader::unknown() /*, parent->listBox()*/ ),
00094       m_url( url ),
00095       m_pixmap( 0L ),
00096       m_parent( parent ),
00097       m_appLocal( false )
00098 {
00099     init( icon, group, description, persistent );
00100 }
00101 
00102 KURLBarItem::KURLBarItem( KURLBar *parent,
00103                           const KURL& url, const QString& description,
00104                           const QString& icon, KIcon::Group group )
00105     : QListBoxPixmap( KIconLoader::unknown() /*, parent->listBox()*/ ),
00106       m_url( url ),
00107       m_pixmap( 0L ),
00108       m_parent( parent ),
00109       m_appLocal( false )
00110 {
00111     init( icon, group, description, true /*persistent*/ );
00112 }
00113 
00114 void KURLBarItem::init( const QString& icon, KIcon::Group group,
00115                         const QString& description, bool persistent )
00116 {
00117     d = new KURLBarItemPrivate;
00118     d->isPersistent = persistent;
00119 
00120     setCustomHighlighting( true );
00121     setIcon( icon, group );
00122     setDescription( description );
00123 }
00124 
00125 KURLBarItem::~KURLBarItem()
00126 {
00127     delete d;
00128 }
00129 
00130 void KURLBarItem::setURL( const KURL& url )
00131 {
00132     m_url = url;
00133     if ( m_description.isEmpty() )
00134         setText( url.fileName() );
00135 }
00136 
00137 void KURLBarItem::setIcon( const QString& icon, KIcon::Group group )
00138 {
00139     m_icon  = icon;
00140     m_group = group;
00141 
00142     if ( icon.isEmpty() )
00143         m_pixmap = KMimeType::pixmapForURL( m_url, 0, group, iconSize() );
00144     else
00145         m_pixmap = KGlobal::iconLoader()->loadIcon( icon, group, iconSize(),
00146                                                     KIcon::DefaultState );
00147 }
00148 
00149 void KURLBarItem::setDescription( const QString& desc )
00150 {
00151     m_description = desc;
00152     setText( desc.isEmpty() ? m_url.fileName() : desc );
00153 }
00154 
00155 void KURLBarItem::setApplicationLocal( bool local )
00156 {
00157     if ( !local && !isPersistent() )
00158     {
00159         kdWarning() << "KURLBar: dynamic (non-persistent) items can not be global." << endl;
00160         return;
00161     }
00162 
00163     m_appLocal = local;
00164 }
00165 
00166 void KURLBarItem::setToolTip( const QString& tip )
00167 {
00168     m_toolTip = tip;
00169 }
00170 
00171 QString KURLBarItem::toolTip() const
00172 {
00173     return m_toolTip.isEmpty() ? m_url.prettyURL() : m_toolTip;
00174 }
00175 
00176 int KURLBarItem::iconSize() const
00177 {
00178     return m_parent->iconSize();
00179 }
00180 
00181 void KURLBarItem::paint( QPainter *p )
00182 {
00183     QListBox *box = listBox();
00184     int w = width( box );
00185     static const int margin = KDialog::spacingHint();
00186 
00187     // draw sunken selection
00188     if ( isCurrent() || isSelected() ) {
00189         int h = height( box );
00190 
00191         QBrush brush = box->colorGroup().brush( QColorGroup::Highlight );
00192         p->fillRect( 0, 0, w, h, brush );
00193         QPen pen = p->pen();
00194         QPen oldPen = pen;
00195         pen.setColor( box->colorGroup().mid() );
00196         p->setPen( pen );
00197 
00198         p->drawPoint( 0, 0 );
00199         p->drawPoint( 0, h - 1 );
00200         p->drawPoint( w - 1, 0 );
00201         p->drawPoint( w - 1, h - 1 );
00202 
00203         p->setPen( oldPen );
00204     }
00205 
00206     if ( m_parent->iconSize() < KIcon::SizeMedium ) {
00207         // small icon -> draw icon next to text
00208 
00209         // ### mostly cut & paste of QListBoxPixmap::paint() until Qt 3.1
00210         // (where it will properly use pixmap() instead of the internal pixmap)
00211         const QPixmap *pm = pixmap();
00212         int yPos = QMAX( 0, (height(box) - pm->height())/2 );
00213 
00214         p->drawPixmap( margin, yPos, *pm );
00215         if ( !text().isEmpty() ) {
00216             QFontMetrics fm = p->fontMetrics();
00217             if ( pm->height() < fm.height() )
00218                 yPos = fm.ascent() + fm.leading()/2;
00219             else
00220                 yPos = pm->height()/2 - fm.height()/2 + fm.ascent();
00221 
00222             yPos += margin;
00223             int stringWidth = box->width() - pm->width() - 2 - (margin * 2);
00224             QString visibleText = KStringHandler::rPixelSqueeze( text(), fm, stringWidth );
00225             int xPos = pm->width() + margin + 2;
00226 
00227             if ( isCurrent() || isSelected() ) {
00228                 p->setPen( box->colorGroup().highlight().dark(115) );
00229                 p->drawText( xPos + ( QApplication::reverseLayout() ? -1 : 1),
00230                              yPos + 1, visibleText );
00231                 p->setPen( box->colorGroup().highlightedText() );
00232             }
00233 
00234             p->drawText( xPos, yPos, visibleText );
00235         }
00236         // end cut & paste (modulo pixmap centering)
00237     }
00238 
00239     else {
00240         // big icons -> draw text below icon
00241         int y = margin;
00242         const QPixmap *pm = pixmap();
00243 
00244         if ( !pm->isNull() ) {
00245             int x = (w - pm->width()) / 2;
00246             x = QMAX( x, margin );
00247             p->drawPixmap( x, y, *pm );
00248         }
00249 
00250         if ( !text().isEmpty() ) {
00251             QFontMetrics fm = p->fontMetrics();
00252             y += pm->height() + fm.height() - fm.descent();
00253 
00254             int stringWidth = box->width() - (margin * 2);
00255             QString visibleText = KStringHandler::rPixelSqueeze( text(), fm, stringWidth );
00256             int x = (w - fm.width( visibleText )) / 2;
00257             x = QMAX( x, margin );
00258 
00259             if ( isCurrent() || isSelected() ) {
00260                 p->setPen( box->colorGroup().highlight().dark(115) );
00261                 p->drawText( x + ( QApplication::reverseLayout() ? -1 : 1),
00262                              y + 1, visibleText );
00263                 p->setPen( box->colorGroup().highlightedText() );
00264             }
00265 
00266             p->drawText( x, y, visibleText );
00267         }
00268     }
00269 }
00270 
00271 QSize KURLBarItem::sizeHint() const
00272 {
00273     int wmin = 0;
00274     int hmin = 0;
00275     const KURLBarListBox *lb =static_cast<const KURLBarListBox*>(listBox());
00276 
00277     if ( m_parent->iconSize() < KIcon::SizeMedium ) {
00278         wmin = QListBoxPixmap::width( lb ) + KDialog::spacingHint() * 2;
00279         hmin = QListBoxPixmap::height( lb ) + KDialog::spacingHint() * 2;
00280     }
00281     else {
00282         wmin = QMAX(lb->fontMetrics().width(text()), pixmap()->width()) + KDialog::spacingHint() * 2;
00283         hmin = lb->fontMetrics().lineSpacing() + pixmap()->height() + KDialog::spacingHint() * 2;
00284     }
00285 
00286     if ( lb->isVertical() )
00287         wmin = QMIN( wmin, lb->viewport()->sizeHint().width() );
00288     else
00289         hmin = QMIN( hmin, lb->viewport()->sizeHint().height() );
00290 
00291     return QSize( wmin, hmin );
00292 }
00293 
00294 int KURLBarItem::width( const QListBox *lb ) const
00295 {
00296     if ( static_cast<const KURLBarListBox *>( lb )->isVertical() )
00297         return QMAX( sizeHint().width(), lb->viewport()->width() );
00298     else
00299         return sizeHint().width();
00300 }
00301 
00302 int KURLBarItem::height( const QListBox *lb ) const
00303 {
00304     if ( static_cast<const KURLBarListBox *>( lb )->isVertical() )
00305         return sizeHint().height();
00306     else
00307         return QMAX( sizeHint().height(), lb->viewport()->height() );
00308 }
00309 
00310 bool KURLBarItem::isPersistent() const
00311 {
00312     return d->isPersistent;
00313 }
00314 
00317 
00318 class KURLBar::KURLBarPrivate
00319 {
00320 public:
00321     KURLBarPrivate()
00322     {
00323         currentURL.setPath( QDir::homeDirPath() );
00324         defaultIconSize = 0;
00325     }
00326 
00327     int defaultIconSize;
00328     KURL currentURL;
00329 };
00330 
00331 
00332 KURLBar::KURLBar( bool useGlobalItems, QWidget *parent, const char *name, WFlags f )
00333     : QFrame( parent, name, f ),
00334       m_activeItem( 0L ),
00335       m_useGlobal( useGlobalItems ),
00336       m_isModified( false ),
00337       m_isImmutable( false ),
00338       m_listBox( 0L ),
00339       m_iconSize( KIcon::SizeMedium )
00340 {
00341     d = new KURLBarPrivate();
00342 
00343     setListBox( 0L );
00344     setSizePolicy( QSizePolicy( isVertical() ?
00345                                 QSizePolicy::Maximum :
00346                                 QSizePolicy::Preferred,
00347                                 isVertical() ?
00348                                 QSizePolicy::Preferred :
00349                                 QSizePolicy::Maximum ));
00350     QWhatsThis::add(this, i18n("<qt>The <b>Quick Access</b> panel provides easy access to commonly used file locations.<p>"
00351                                "Clicking on one of the shortcut entries will take you to that location.<p>"
00352                                "By right clicking on an entry you can add, edit and remove shortcuts.</qt>"));
00353 }
00354 
00355 KURLBar::~KURLBar()
00356 {
00357     delete d;
00358 }
00359 
00360 KURLBarItem * KURLBar::insertItem(const KURL& url, const QString& description,
00361                                   bool applicationLocal,
00362                                   const QString& icon, KIcon::Group group )
00363 {
00364     KURLBarItem *item = new KURLBarItem(this, url, description, icon, group);
00365     item->setApplicationLocal( applicationLocal );
00366     m_listBox->insertItem( item );
00367     return item;
00368 }
00369 
00370 KURLBarItem * KURLBar::insertDynamicItem(const KURL& url, const QString& description,
00371                                          const QString& icon, KIcon::Group group )
00372 {
00373     KURLBarItem *item = new KURLBarItem(this, url, false, description, icon, group);
00374     m_listBox->insertItem( item );
00375     return item;
00376 }
00377 
00378 void KURLBar::setOrientation( Qt::Orientation orient )
00379 {
00380     m_listBox->setOrientation( orient );
00381     setSizePolicy( QSizePolicy( isVertical() ?
00382                                 QSizePolicy::Maximum :
00383                                 QSizePolicy::Preferred,
00384                                 isVertical() ?
00385                                 QSizePolicy::Preferred :
00386                                 QSizePolicy::Maximum ));
00387 }
00388 
00389 Qt::Orientation KURLBar::orientation() const
00390 {
00391     return m_listBox->orientation();
00392 }
00393 
00394 void KURLBar::setListBox( KURLBarListBox *view )
00395 {
00396     delete m_listBox;
00397 
00398     if ( !view ) {
00399         m_listBox = new KURLBarListBox( this, "urlbar listbox" );
00400         setOrientation( Vertical );
00401     }
00402     else {
00403         m_listBox = view;
00404         if ( m_listBox->parentWidget() != this )
00405             m_listBox->reparent( this, QPoint(0,0) );
00406         m_listBox->resize( width(), height() );
00407     }
00408 
00409     m_listBox->setSelectionMode( KListBox::Single );
00410     paletteChange( palette() );
00411     m_listBox->setFocusPolicy( TabFocus );
00412 
00413     connect( m_listBox, SIGNAL( mouseButtonClicked( int, QListBoxItem *, const QPoint & ) ),
00414              SLOT( slotSelected( int, QListBoxItem * )));
00415     connect( m_listBox, SIGNAL( dropped( QDropEvent * )),
00416              this, SLOT( slotDropped( QDropEvent * )));
00417     connect( m_listBox, SIGNAL( contextMenuRequested( QListBoxItem *,
00418                                                       const QPoint& )),
00419              SLOT( slotContextMenuRequested( QListBoxItem *, const QPoint& )));
00420     connect( m_listBox, SIGNAL( returnPressed( QListBoxItem * ) ),
00421              SLOT( slotSelected( QListBoxItem * ) ));
00422 }
00423 
00424 void KURLBar::setIconSize( int size )
00425 {
00426     if ( size == m_iconSize )
00427         return;
00428 
00429     m_iconSize = size;
00430 
00431     // reload the icons with the new size
00432     KURLBarItem *item = static_cast<KURLBarItem*>( m_listBox->firstItem() );
00433     while ( item ) {
00434         item->setIcon( item->icon(), item->iconGroup() );
00435         item = static_cast<KURLBarItem*>( item->next() );
00436     }
00437 
00438     resize( sizeHint() );
00439     updateGeometry();
00440 }
00441 
00442 void KURLBar::clear()
00443 {
00444     m_listBox->clear();
00445 }
00446 
00447 void KURLBar::resizeEvent( QResizeEvent *e )
00448 {
00449     QFrame::resizeEvent( e );
00450     m_listBox->resize( width(), height() );
00451 }
00452 
00453 void KURLBar::paletteChange( const QPalette & )
00454 {
00455     QPalette pal = palette();
00456     QColor gray = pal.color( QPalette::Normal, QColorGroup::Background );
00457     QColor selectedTextColor = pal.color( QPalette::Normal, QColorGroup::BrightText );
00458     QColor foreground = pal.color( QPalette::Normal, QColorGroup::Foreground );
00459     pal.setColor( QPalette::Normal,   QColorGroup::Base, gray );
00460     pal.setColor( QPalette::Normal,   QColorGroup::HighlightedText, selectedTextColor );
00461     pal.setColor( QPalette::Normal,   QColorGroup::Text, foreground );
00462     pal.setColor( QPalette::Inactive, QColorGroup::Base, gray );
00463     pal.setColor( QPalette::Inactive, QColorGroup::HighlightedText, selectedTextColor );
00464     pal.setColor( QPalette::Inactive, QColorGroup::Text, foreground );
00465 
00466     setPalette( pal );
00467 }
00468 
00469 QSize KURLBar::sizeHint() const
00470 {
00471     return m_listBox->sizeHint();
00472 
00473 #if 0
00474     // this code causes vertical and or horizontal scrollbars appearing
00475     // depending on the text, font, moonphase and earth rotation. Just using
00476     // m_listBox->sizeHint() fixes this (although the widget can then be
00477     // resized to a smaller size so that scrollbars appear).
00478     int w = 0;
00479     int h = 0;
00480     KURLBarItem *item;
00481     bool vertical = isVertical();
00482 
00483     for ( item = static_cast<KURLBarItem*>( m_listBox->firstItem() );
00484           item;
00485           item = static_cast<KURLBarItem*>( item->next() ) ) {
00486 
00487         QSize sh = item->sizeHint();
00488 
00489         if ( vertical ) {
00490             w = QMAX( w, sh.width() );
00491             h += sh.height();
00492         }
00493         else {
00494             w += sh.width();
00495             h = QMAX( h, sh.height() );
00496         }
00497     }
00498 
00499 //     if ( vertical && m_listBox->verticalScrollBar()->isVisible() )
00500 //         w += m_listBox->verticalScrollBar()->width();
00501 //     else if ( !vertical && m_listBox->horizontalScrollBar()->isVisible() )
00502 //         h += m_listBox->horizontalScrollBar()->height();
00503 
00504     if ( w == 0 && h == 0 )
00505         return QSize( 100, 200 );
00506     else
00507         return QSize( 6 + w, h );
00508 #endif
00509 }
00510 
00511 QSize KURLBar::minimumSizeHint() const
00512 {
00513     QSize s = sizeHint(); // ###
00514     int w = s.width()  + m_listBox->verticalScrollBar()->width();
00515     int h = s.height() + m_listBox->horizontalScrollBar()->height();
00516     return QSize( w, h );
00517 }
00518 
00519 void KURLBar::slotSelected( int button, QListBoxItem *item )
00520 {
00521     if ( button != Qt::LeftButton )
00522         return;
00523 
00524     slotSelected( item );
00525 }
00526 
00527 void KURLBar::slotSelected( QListBoxItem *item )
00528 {
00529     if ( item && item != m_activeItem )
00530         m_activeItem = static_cast<KURLBarItem*>( item );
00531 
00532     if ( m_activeItem ) {
00533         m_listBox->setCurrentItem( m_activeItem );
00534         emit activated( m_activeItem->url() );
00535     }
00536 }
00537 
00538 void KURLBar::setCurrentItem( const KURL& url )
00539 {
00540     d->currentURL = url;
00541 
00542     QString u = url.url(-1);
00543 
00544     if ( m_activeItem && m_activeItem->url().url(-1) == u )
00545         return;
00546 
00547     bool hasURL = false;
00548     QListBoxItem *item = m_listBox->firstItem();
00549     while ( item ) {
00550         if ( static_cast<KURLBarItem*>( item )->url().url(-1) == u ) {
00551             m_activeItem = static_cast<KURLBarItem*>( item );
00552             m_listBox->setCurrentItem( item );
00553             m_listBox->setSelected( item, true );
00554             hasURL = true;
00555             break;
00556         }
00557         item = item->next();
00558     }
00559 
00560     if ( !hasURL ) {
00561         m_activeItem = 0L;
00562         m_listBox->clearSelection();
00563     }
00564 }
00565 
00566 KURLBarItem * KURLBar::currentItem() const
00567 {
00568     QListBoxItem *item = m_listBox->item( m_listBox->currentItem() );
00569     if ( item )
00570         return static_cast<KURLBarItem *>( item );
00571     return 0L;
00572 }
00573 
00574 KURL KURLBar::currentURL() const
00575 {
00576     KURLBarItem *item = currentItem();
00577     return item ? item->url() : KURL();
00578 }
00579 
00580 void KURLBar::readConfig( KConfig *appConfig, const QString& itemGroup )
00581 {
00582     m_isImmutable = appConfig->groupIsImmutable( itemGroup );
00583     KConfigGroupSaver cs( appConfig, itemGroup );
00584     d->defaultIconSize = m_iconSize;
00585     m_iconSize = appConfig->readNumEntry( "Speedbar IconSize", m_iconSize );
00586 
00587     if ( m_useGlobal ) { // read global items
00588         KConfig *globalConfig = KGlobal::config();
00589         KConfigGroupSaver cs( globalConfig, (QString)(itemGroup +" (Global)"));
00590         int num = globalConfig->readNumEntry( "Number of Entries" );
00591         for ( int i = 0; i < num; i++ ) {
00592             readItem( i, globalConfig, false );
00593         }
00594     }
00595 
00596     // read application local items
00597     int num = appConfig->readNumEntry( "Number of Entries" );
00598     for ( int i = 0; i < num; i++ ) {
00599         readItem( i, appConfig, true );
00600     }
00601 }
00602 
00603 void KURLBar::readItem( int i, KConfig *config, bool applicationLocal )
00604 {
00605     QString number = QString::number( i );
00606     KURL url = KURL::fromPathOrURL( config->readPathEntry( QString("URL_") + number ));
00607     if ( !url.isValid() || !KProtocolInfo::isKnownProtocol( url ) ||
00608             (url.isLocalFile() && !QFile(url.path()).exists()))
00609         return; // nothing we could do.
00610 
00611     insertItem( url,
00612                 config->readEntry( QString("Description_") + number ),
00613                 applicationLocal,
00614                 config->readEntry( QString("Icon_") + number ),
00615                 static_cast<KIcon::Group>(
00616                     config->readNumEntry( QString("IconGroup_") + number )) );
00617 }
00618 
00619 void KURLBar::writeConfig( KConfig *config, const QString& itemGroup )
00620 {
00621     KConfigGroupSaver cs1( config, itemGroup );
00622     if(!config->hasDefault("Speedbar IconSize") && m_iconSize == d->defaultIconSize )
00623         config->revertToDefault("Speedbar IconSize");
00624     else
00625         config->writeEntry( "Speedbar IconSize", m_iconSize );
00626 
00627     if ( !m_isModified )
00628         return;
00629 
00630     int i = 0;
00631     int numLocal = 0;
00632     KURLBarItem *item = static_cast<KURLBarItem*>( m_listBox->firstItem() );
00633 
00634     while ( item )
00635     {
00636         if ( item->isPersistent() ) // we only save persistent items
00637         {
00638             if ( item->applicationLocal() )
00639             {
00640                 writeItem( item, numLocal, config, false );
00641                 numLocal++;
00642             }
00643 
00644             i++;
00645         }
00646         item = static_cast<KURLBarItem*>( item->next() );
00647     }
00648     config->writeEntry("Number of Entries", numLocal);
00649 
00650 
00651     // write the global entries to kdeglobals, if any
00652     bool haveGlobalEntries = (i > numLocal);
00653     if ( m_useGlobal && haveGlobalEntries ) {
00654         config->setGroup( itemGroup + " (Global)" );
00655 
00656         int numGlobals = 0;
00657         item = static_cast<KURLBarItem*>( m_listBox->firstItem() );
00658 
00659         while ( item )
00660         {
00661             if ( item->isPersistent() ) // we only save persistent items
00662             {
00663                 if ( !item->applicationLocal() )
00664                 {
00665                     writeItem( item, numGlobals, config, true );
00666                     numGlobals++;
00667                 }
00668             }
00669 
00670             item = static_cast<KURLBarItem*>( item->next() );
00671         }
00672         config->writeEntry("Number of Entries", numGlobals, true, true);
00673     }
00674 
00675     m_isModified = false;
00676 }
00677 
00678 void KURLBar::writeItem( KURLBarItem *item, int i, KConfig *config,
00679                          bool global )
00680 {
00681     if ( !item->isPersistent() )
00682         return;
00683 
00684     QString Description = "Description_";
00685     QString URL = "URL_";
00686     QString Icon = "Icon_";
00687     QString IconGroup = "IconGroup_";
00688 
00689     QString number = QString::number( i );
00690     config->writePathEntry( URL + number, item->url().prettyURL(), true, global );
00691 
00692     config->writeEntry( Description + number, item->description(),true,global);
00693     config->writeEntry( Icon + number, item->icon(), true, global );
00694     config->writeEntry( IconGroup + number, item->iconGroup(), true, global );
00695 }
00696 
00697 
00698 void KURLBar::slotDropped( QDropEvent *e )
00699 {
00700     KURL::List urls;
00701     if ( KURLDrag::decode( e, urls ) ) {
00702         KURL url;
00703         QString description;
00704         QString icon;
00705         bool appLocal = false;
00706 
00707         KURL::List::Iterator it = urls.begin();
00708         for ( ; it != urls.end(); ++it ) {
00709             (void) insertItem( *it, description, appLocal, icon );
00710             if( !appLocal)
00711                     createItemOnMDKMerge( url, description, icon );
00712             m_isModified = true;
00713             updateGeometry();
00714         }
00715     }
00716 }
00717 
00718 void KURLBar::slotContextMenuRequested( QListBoxItem *_item, const QPoint& pos )
00719 {
00720     if (m_isImmutable)
00721         return;
00722 
00723     KURLBarItem *item = dynamic_cast<KURLBarItem*>( _item );
00724 
00725     static const int IconSize   = 10;
00726     static const int AddItem    = 20;
00727     static const int EditItem   = 30;
00728     static const int RemoveItem = 40;
00729 
00730     KURL lastURL = m_activeItem ? m_activeItem->url() : KURL();
00731 
00732     bool smallIcons = m_iconSize < KIcon::SizeMedium;
00733     QPopupMenu *popup = new QPopupMenu();
00734     popup->insertItem( smallIcons ?
00735                        i18n("&Large Icons") : i18n("&Small Icons"),
00736                        IconSize );
00737     popup->insertSeparator();
00738 
00739     if (item != 0L && item->isPersistent())
00740     {
00741         popup->insertItem(SmallIconSet("edit"), i18n("&Edit Entry..."), EditItem);
00742         popup->insertSeparator();
00743     }
00744 
00745     popup->insertItem(SmallIconSet("filenew"), i18n("&Add Entry..."), AddItem);
00746 
00747     if (item != 0L && item->isPersistent())
00748     {
00749         popup->insertItem( SmallIconSet("editdelete"), i18n("&Remove Entry"),
00750                           RemoveItem );
00751     }
00752 
00753     int result = popup->exec( pos );
00754     switch ( result ) {
00755         case IconSize:
00756             setIconSize( smallIcons ? KIcon::SizeMedium : KIcon::SizeSmallMedium );
00757             m_listBox->triggerUpdate( true );
00758             break;
00759         case AddItem:
00760             addNewItem();
00761             break;
00762         case EditItem:
00763             editItem( static_cast<KURLBarItem *>( item ) );
00764             break;
00765         case RemoveItem:
00766             delete item;
00767             m_isModified = true;
00768             break;
00769         default: // abort
00770             break;
00771     }
00772 
00773     // reset current item
00774     m_activeItem = 0L;
00775     setCurrentItem( lastURL );
00776 }
00777 
00778 bool KURLBar::addNewItem()
00779 {
00780     KURLBarItem *item = new KURLBarItem( this, d->currentURL,
00781                                          i18n("Enter a description") );
00782     if ( editItem( item ) ) {
00783         m_listBox->insertItem( item );
00784         return true;
00785     }
00786 
00787     delete item;
00788     return false;
00789 }
00790 
00791 bool KURLBar::editItem( KURLBarItem *item )
00792 {
00793     if ( !item || !item->isPersistent() ) // should never happen tho
00794         return false;
00795     QString oldDescription = item->description();
00796     KURL url            = item->url();
00797     QString description = item->description();
00798     QString icon        = item->icon();
00799     bool appLocal       = item->applicationLocal();
00800 
00801     if ( KURLBarItemDialog::getInformation( m_useGlobal,
00802                                             url, description,
00803                                             icon, appLocal,
00804                                             m_iconSize, this ))
00805     {
00806        if( !appLocal)
00807                createItemOnMDKMerge( url, description, icon );        
00808         item->setURL( url );
00809         item->setDescription( description );
00810         item->setIcon( icon );
00811         item->setApplicationLocal( appLocal );
00812         m_listBox->triggerUpdate( true );
00813         m_isModified = true;
00814         updateGeometry();
00815         return true;
00816     }
00817 
00818     return false;
00819 }
00820 
00821 void  KURLBar::createItemOnMDKMerge( const KURL &url, const QString & description, const QString &icon )
00822 {
00823    if ( !QFile::exists( KStandardDirs::mandrake_merge_directory() ) )
00824        KStandardDirs::makeDir( QFile::encodeName( KStandardDirs::mandrake_merge_directory() ) );
00825     KDesktopFile df(KStandardDirs::mandrake_merge_directory() + description);
00826     df.writeEntry( "Name", description );
00827     df.writeEntry( "Icon", icon );
00828     df.writeEntry( "Type", "Link" );
00829     df.writeEntry( "URL", url.url() );
00830     df.sync();
00831 }
00832 
00835 
00836 
00837 KURLBarListBox::KURLBarListBox( QWidget *parent, const char *name )
00838     : KListBox( parent, name )
00839 {
00840     m_toolTip = new KURLBarToolTip( this );
00841     setAcceptDrops( true );
00842     viewport()->setAcceptDrops( true );
00843 }
00844 
00845 KURLBarListBox::~KURLBarListBox()
00846 {
00847     delete m_toolTip;
00848 }
00849 
00850 void KURLBarListBox::paintEvent( QPaintEvent* )
00851 {
00852     QPainter p(this);
00853     p.setPen( colorGroup().mid() );
00854     p.drawRect( 0, 0, width(), height() );
00855 }
00856 
00857 QDragObject * KURLBarListBox::dragObject()
00858 {
00859     KURL::List urls;
00860     KURLBarItem *item = static_cast<KURLBarItem*>( firstItem() );
00861 
00862     while ( item ) {
00863         if ( item->isSelected() )
00864             urls.append( item->url() );
00865         item = static_cast<KURLBarItem*>( item->next() );
00866     }
00867 
00868     if ( !urls.isEmpty() ) // ### use custom drag-object with description etc.?
00869         return new KURLDrag( urls, this, "urlbar drag" );
00870 
00871     return 0L;
00872 }
00873 
00874 void KURLBarListBox::contentsDragEnterEvent( QDragEnterEvent *e )
00875 {
00876     e->accept( KURLDrag::canDecode( e ));
00877 }
00878 
00879 void KURLBarListBox::contentsDropEvent( QDropEvent *e )
00880 {
00881     emit dropped( e );
00882 }
00883 
00884 void KURLBarListBox::contextMenuEvent( QContextMenuEvent *e )
00885 {
00886     if (e)
00887     {
00888         emit contextMenuRequested( itemAt( e->globalPos() ), e->globalPos() );
00889         e->consume(); // Consume the event to avoid multiple contextMenuEvent calls...
00890     }
00891 }
00892 
00893 void KURLBarListBox::setOrientation( Qt::Orientation orient )
00894 {
00895     if ( orient == Vertical ) {
00896         setColumnMode( 1 );
00897         setRowMode( Variable );
00898     }
00899     else {
00900         setRowMode( 1 );
00901         setColumnMode( Variable );
00902     }
00903 
00904     m_orientation = orient;
00905 }
00906 
00909 
00910 
00911 bool KURLBarItemDialog::getInformation( bool allowGlobal, KURL& url,
00912                                         QString& description, QString& icon,
00913                                         bool& appLocal, int iconSize,
00914                                         QWidget *parent )
00915 {
00916     KURLBarItemDialog *dialog = new KURLBarItemDialog( allowGlobal, url,
00917                                                        description, icon,
00918                                                        appLocal,
00919                                                        iconSize, parent );
00920     if ( dialog->exec() == QDialog::Accepted ) {
00921         // set the return parameters
00922         url         = dialog->url();
00923         description = dialog->description();
00924         icon        = dialog->icon();
00925         appLocal    = dialog->applicationLocal();
00926 
00927         delete dialog;
00928         return true;
00929     }
00930 
00931     delete dialog;
00932     return false;
00933 }
00934 
00935 KURLBarItemDialog::KURLBarItemDialog( bool allowGlobal, const KURL& url,
00936                                       const QString& description,
00937                                       QString icon, bool appLocal,
00938                                       int iconSize,
00939                                       QWidget *parent, const char *name )
00940     : KDialogBase( parent, name, true,
00941                    i18n("Edit Quick Access Entry"), Ok | Cancel, Ok, true )
00942 {
00943     QVBox *box = new QVBox( this );
00944     QString text = i18n("<qt><b>Please provide a description, URL and icon for this Quick Access entry.</b></br></qt>");
00945     QLabel *label = new QLabel( text, box );
00946     box->setSpacing( spacingHint() );
00947 
00948     QGrid *grid = new QGrid( 2, box );
00949     grid->setSpacing( spacingHint() );
00950 
00951     QString whatsThisText = i18n("<qt>This is the text that will appear in the Quick Access panel.<p>"
00952                                  "The description should consist of one or two words "
00953                                  "that will help you remember what this entry refers to.</qt>");
00954     label = new QLabel( i18n("&Description:"), grid );
00955     m_edit = new KLineEdit( grid, "description edit" );
00956     m_edit->setText( description.isEmpty() ? url.fileName() : description );
00957     label->setBuddy( m_edit );
00958     QWhatsThis::add( label, whatsThisText );
00959     QWhatsThis::add( m_edit, whatsThisText );
00960 
00961     whatsThisText = i18n("<qt>This is the location associated with the entry. Any valid URL may be used. For example:<p>"
00962                          "%1<br>http://www.kde.org<br>ftp://ftp.kde.org/pub/kde/stable<p>"
00963                          "By clicking on the button next to the text edit box you can browse to an "
00964                          "appropriate URL.</qt>").arg(QDir::homeDirPath());
00965     label = new QLabel( i18n("&URL:"), grid );
00966     m_urlEdit = new KURLRequester( url.prettyURL(), grid );
00967     m_urlEdit->setMode( KFile::Directory );
00968     label->setBuddy( m_urlEdit );
00969     QWhatsThis::add( label, whatsThisText );
00970     QWhatsThis::add( m_urlEdit, whatsThisText );
00971 
00972     whatsThisText = i18n("<qt>This is the icon that will appear in the Quick Access panel.<p>"
00973                          "Click on the button to select a different icon.</qt>");
00974     label = new QLabel( i18n("Choose an &icon:"), grid );
00975     m_iconButton = new KIconButton( grid, "icon button" );
00976     m_iconButton->setIconSize( iconSize );
00977     if ( icon.isEmpty() )
00978         icon = KMimeType::iconForURL( url );
00979     m_iconButton->setIcon( icon );
00980     label->setBuddy( m_iconButton );
00981     QWhatsThis::add( label, whatsThisText );
00982     QWhatsThis::add( m_iconButton, whatsThisText );
00983 
00984     if ( allowGlobal ) {
00985         QString appName;
00986         if ( KGlobal::instance()->aboutData() )
00987             appName = KGlobal::instance()->aboutData()->programName();
00988         if ( appName.isEmpty() )
00989             appName = QString::fromLatin1( KGlobal::instance()->instanceName() );
00990         m_appLocal = new QCheckBox( i18n("&Only show when using this application (%1)").arg( appName ), box );
00991         m_appLocal->setChecked( appLocal );
00992         QWhatsThis::add( m_appLocal,
00993                          i18n("<qt>Select this setting if you want this "
00994                               "entry to show only when using the current application (%1).<p>"
00995                               "If this setting is not selected, the entry will be available in all "
00996                               "applications.</qt>")
00997                               .arg(appName));
00998     }
00999     else
01000         m_appLocal = 0L;
01001     connect(m_urlEdit->lineEdit(),SIGNAL(textChanged ( const QString & )),this,SLOT(urlChanged(const QString & )));
01002     m_edit->setFocus();
01003     setMainWidget( box );
01004 }
01005 
01006 KURLBarItemDialog::~KURLBarItemDialog()
01007 {
01008 }
01009 
01010 void KURLBarItemDialog::urlChanged(const QString & text )
01011 {
01012     enableButtonOK( !text.isEmpty() );
01013 }
01014 
01015 KURL KURLBarItemDialog::url() const
01016 {
01017     QString text = m_urlEdit->url();
01018     KURL u;
01019     if ( text.at(0) == '/' )
01020         u.setPath( text );
01021     else
01022         u = text;
01023 
01024     return u;
01025 }
01026 
01027 QString KURLBarItemDialog::description() const
01028 {
01029     return m_edit->text();
01030 }
01031 
01032 QString KURLBarItemDialog::icon() const
01033 {
01034     return m_iconButton->icon();
01035 }
01036 
01037 bool KURLBarItemDialog::applicationLocal() const
01038 {
01039     if ( !m_appLocal )
01040         return true;
01041 
01042     return m_appLocal->isChecked();
01043 }
01044 
01045 void KURLBarItem::virtual_hook( int, void* )
01046 { /*BASE::virtual_hook( id, data );*/ }
01047 
01048 void KURLBar::virtual_hook( int, void* )
01049 { /*BASE::virtual_hook( id, data );*/ }
01050 
01051 void KURLBarListBox::virtual_hook( int id, void* data )
01052 { KListBox::virtual_hook( id, data ); }
01053 
01054 
01055 #include "kurlbar.moc"
KDE Logo
This file is part of the documentation for kio Library Version 3.4.2.
Documentation copyright © 1996-2004 the KDE developers.
Generated on Fri Sep 16 06:56:31 2005 by doxygen 1.4.4 written by Dimitri van Heesch, © 1997-2003