1
/* This file is part of the KDE projects
2
Copyright (C) 2000 David Faure <faure@kde.org>
4
This program is free software; you can redistribute it and/or
5
modify it under the terms of the GNU General Public
6
License as published by the Free Software Foundation; either
7
version 2 of the License, or (at your option) any later version.
9
This program is distributed in the hope that it will be useful,
10
but WITHOUT ANY WARRANTY; without even the implied warranty of
11
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12
General Public License for more details.
14
You should have received a copy of the GNU General Public License
15
along with this program; see the file COPYING. If not, write to
16
the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
17
Boston, MA 02111-1307, USA.
20
#include "konq_dirpart.h"
21
#include "konq_bgnddlg.h"
22
#include "konq_propsview.h"
23
#include "konq_settings.h"
26
#include <kdatastream.h>
27
#include <kcolordialog.h>
29
#include <kiconloader.h>
31
#include <kmessagebox.h>
32
#include <konq_drag.h>
33
#include <kparts/browserextension.h>
35
#include <kuserprofile.h>
36
#include <kurifilter.h>
37
#include <kglobalsettings.h>
39
#include <qapplication.h>
40
#include <qclipboard.h>
44
class KonqDirPart::KonqDirPartPrivate
47
QStringList mimeFilters;
50
KonqDirPart::KonqDirPart( QObject *parent, const char *name )
51
:KParts::ReadOnlyPart( parent, name ),
55
d = new KonqDirPartPrivate;
59
//m_bMultipleItemsSelected = false;
61
connect( QApplication::clipboard(), SIGNAL(dataChanged()), this, SLOT(slotClipboardDataChanged()) );
63
actionCollection()->setHighlightingEnabled( true );
65
m_paIncIconSize = new KAction( i18n( "Increase Icon Size" ), "viewmag+", 0, this, SLOT( slotIncIconSize() ), actionCollection(), "incIconSize" );
66
m_paDecIconSize = new KAction( i18n( "Decrease Icon Size" ), "viewmag-", 0, this, SLOT( slotDecIconSize() ), actionCollection(), "decIconSize" );
68
m_paDefaultIcons = new KRadioAction( i18n( "&Default Size" ), 0, actionCollection(), "modedefault" );
69
m_paHugeIcons = new KRadioAction( i18n( "&Huge" ), 0, actionCollection(), "modehuge" );
70
m_paLargeIcons = new KRadioAction( i18n( "&Large" ), 0, actionCollection(), "modelarge" );
71
m_paMediumIcons = new KRadioAction( i18n( "&Medium" ), 0, actionCollection(), "modemedium" );
72
m_paSmallIcons = new KRadioAction( i18n( "&Small" ), 0, actionCollection(), "modesmall" );
74
m_paDefaultIcons->setExclusiveGroup( "ViewMode" );
75
m_paHugeIcons->setExclusiveGroup( "ViewMode" );
76
m_paLargeIcons->setExclusiveGroup( "ViewMode" );
77
m_paMediumIcons->setExclusiveGroup( "ViewMode" );
78
m_paSmallIcons->setExclusiveGroup( "ViewMode" );
80
connect( m_paDefaultIcons, SIGNAL( toggled( bool ) ), this, SLOT( slotIconSizeToggled( bool ) ) );
81
connect( m_paHugeIcons, SIGNAL( toggled( bool ) ), this, SLOT( slotIconSizeToggled( bool ) ) );
82
connect( m_paLargeIcons, SIGNAL( toggled( bool ) ), this, SLOT( slotIconSizeToggled( bool ) ) );
83
connect( m_paMediumIcons, SIGNAL( toggled( bool ) ), this, SLOT( slotIconSizeToggled( bool ) ) );
84
connect( m_paSmallIcons, SIGNAL( toggled( bool ) ), this, SLOT( slotIconSizeToggled( bool ) ) );
86
// Extract 4 icon sizes from the icon theme. Use 16,32,48,64 as default.
88
m_iIconSize[0] = 0; // Default value
89
m_iIconSize[1] = KIcon::SizeSmall; // 16
90
m_iIconSize[2] = KIcon::SizeMedium; // 32
91
m_iIconSize[3] = KIcon::SizeLarge; // 48
92
m_iIconSize[4] = KIcon::SizeHuge; // 64
93
KIconTheme *root = KGlobal::instance()->iconLoader()->theme();
96
QValueList<int> avSizes = root->querySizes(KIcon::Desktop);
97
QValueList<int>::Iterator it;
98
for (i=1, it=avSizes.begin(); (it!=avSizes.end()) && (i<5); it++, i++)
100
m_iIconSize[i] = *it;
101
//kdDebug(1203) << "m_iIconSize[" << i << "] = " << *it << endl;
105
KAction *a = new KAction( i18n( "Background Color..." ), 0, this, SLOT( slotBackgroundColor() ),
106
actionCollection(), "bgcolor" );
108
a->setStatusText( i18n( "Allows choosing of a background color for this view" ) );
110
a = new KAction( i18n( "Background Image..." ), "background", 0,
111
this, SLOT( slotBackgroundImage() ),
112
actionCollection(), "bgimage" );
114
a->setStatusText( i18n( "Allows choosing a background image for this view" ) );
117
KonqDirPart::~KonqDirPart()
119
// Close the find part with us
124
void KonqDirPart::setMimeFilter (const QStringList& mime)
126
QString u = url().url();
131
if ( mime.isEmpty() )
132
d->mimeFilters.clear();
134
d->mimeFilters = mime;
137
QStringList KonqDirPart::mimeFilter() const
139
return d->mimeFilters;
142
QScrollView * KonqDirPart::scrollWidget()
144
return static_cast<QScrollView *>(widget());
147
void KonqDirPart::slotBackgroundColor()
149
QColor bgndColor = m_pProps->bgColor( widget() );
150
QColor defaultColor = KGlobalSettings::baseColor();
151
if ( KColorDialog::getColor( bgndColor,defaultColor ) == KColorDialog::Accepted )
153
if ( bgndColor.isValid() )
154
m_pProps->setBgColor( bgndColor );
156
m_pProps->setBgColor( defaultColor );
157
m_pProps->setBgPixmapFile( "" );
158
m_pProps->applyColors( scrollWidget()->viewport() );
159
scrollWidget()->viewport()->repaint();
163
void KonqDirPart::slotBackgroundImage()
165
KonqBgndDialog dlg( m_pProps->bgPixmapFile(), instance() );
166
if ( dlg.exec() == KonqBgndDialog::Accepted )
168
m_pProps->setBgPixmapFile( dlg.pixmapFile() );
169
m_pProps->applyColors( scrollWidget()->viewport() );
170
scrollWidget()->viewport()->repaint();
174
void KonqDirPart::lmbClicked( KFileItem * fileItem )
176
KURL url = fileItem->url();
177
if ( !fileItem->isReadable() )
179
// No permissions or local file that doesn't exist - need to find out which
180
if ( ( !fileItem->isLocalFile() ) || QFile::exists( url.path() ) )
182
KMessageBox::error( widget(), i18n("<p>You do not have enough permissions to read <b>%1</b></p>").arg(url.prettyURL()) );
185
KMessageBox::error( widget(), i18n("<p><b>%1</b> doesn't seem to exist anymore</p>").arg(url.prettyURL()) );
189
KParts::URLArgs args;
190
fileItem->determineMimeType();
191
if ( fileItem->isMimeTypeKnown() )
192
args.serviceType = fileItem->mimetype();
193
args.trustedSource = true;
195
if ( fileItem->isLink() && fileItem->isLocalFile() ) // see KFileItem::run
196
url = KURL( url, KURL::encode_string( fileItem->linkDest() ) );
198
if (KonqFMSettings::settings()->alwaysNewWin() && fileItem->isDir()) {
199
//args.frameName = "_blank"; // open new window
200
// We tried the other option, passing the path as framename so that
201
// an existing window for that dir is reused (like MSWindows does when
202
// the similar option is activated and the sidebar is hidden (!)).
203
// But this requires some work, including changing the framename
204
// when navigating, etc. Not very much requested yet, in addition.
205
KParts::WindowArgs wargs;
206
KParts::ReadOnlyPart* dummy;
207
emit m_extension->createNewWindow( url, args, wargs, dummy );
211
kdDebug() << "emit m_extension->openURLRequest( " << url.url() << "," << args.serviceType << ")" << endl;
212
emit m_extension->openURLRequest( url, args );
216
void KonqDirPart::mmbClicked( KFileItem * fileItem )
220
// Optimisation to avoid KRun to call kfmclient that then tells us
221
// to open a window :-)
222
KService::Ptr offer = KServiceTypeProfile::preferredService(fileItem->mimetype(), "Application");
223
//if (offer) kdDebug(1203) << "KonqDirPart::mmbClicked: got service " << offer->desktopEntryName() << endl;
224
if ( offer && offer->desktopEntryName().startsWith("kfmclient") )
226
KParts::URLArgs args;
227
args.serviceType = fileItem->mimetype();
228
emit m_extension->createNewWindow( fileItem->url(), args );
235
m_extension->pasteRequest();
239
void KonqDirPart::saveState( QDataStream& stream )
241
stream << m_nameFilter;
244
void KonqDirPart::restoreState( QDataStream& stream )
246
stream >> m_nameFilter;
249
void KonqDirPart::saveFindState( QDataStream& stream )
251
// assert only doable in KDE4.
252
//assert( m_findPart ); // test done by caller.
256
// When we have a find part, our own URL wasn't saved (see KonqDirPartBrowserExtension)
257
// So let's do it here
260
KParts::BrowserExtension* ext = KParts::BrowserExtension::childObject( m_findPart );
264
ext->saveState( stream );
267
void KonqDirPart::restoreFindState( QDataStream& stream )
269
// Restore our own URL
272
emit findOpen( this );
274
KParts::BrowserExtension* ext = KParts::BrowserExtension::childObject( m_findPart );
280
ext->restoreState( stream );
283
void KonqDirPart::slotClipboardDataChanged()
285
// This is very related to KDIconView::slotClipboardDataChanged
288
QMimeSource *data = QApplication::clipboard()->data();
289
if ( data->provides( "application/x-kde-cutselection" ) && data->provides( "text/uri-list" ) )
290
if ( KonqDrag::decodeIsCutSelection( data ) )
291
(void) KURLDrag::decode( data, lst );
298
void KonqDirPart::updatePasteAction()
300
QMimeSource *data = QApplication::clipboard()->data();
301
bool paste = ( data->format() != 0 );
303
emit m_extension->enableAction( "paste", paste ); // TODO : if only one url, check that it's a dir
306
void KonqDirPart::newItems( const KFileItemList & entries )
308
for (KFileItemListIterator it(entries); it.current(); ++it)
310
if ( !it.current()->isDir() )
312
if (!it.current()->isLink()) // ignore symlinks
313
m_lDirSize += it.current()->size();
322
emit itemsAdded( entries );
325
void KonqDirPart::deleteItem( KFileItem * fileItem )
327
if ( !fileItem->isDir() )
329
if ( !fileItem->isLink() )
330
m_lDirSize -= fileItem->size();
336
emit itemRemoved( fileItem );
339
void KonqDirPart::emitTotalCount()
342
KIO::itemsSummaryString(m_lFileCount + m_lDirCount,
347
bool bShowsResult = false;
350
QVariant prop = m_findPart->property( "showsResult" );
351
bShowsResult = prop.isValid() && prop.toBool();
353
//kdDebug(1203) << "KonqDirPart::emitTotalCount bShowsResult=" << bShowsResult << endl;
354
emit setStatusBarText( bShowsResult ? i18n("Search result: %1").arg(summary) : summary );
357
void KonqDirPart::emitCounts( const KFileItemList & lst, bool selectionChanged )
359
// Compare the new value with our cache
360
/*bool multiple = lst.count()>1;
361
if (multiple != m_bMultipleItemsSelected)
363
m_bMultipleItemsSelected = multiple;
369
emit setStatusBarText( ((KFileItemList)lst).first()->getStatusBarInfo() );
371
else if ( lst.count()>1)
373
long long fileSizeSum = 0;
377
for (KFileItemListIterator it( lst ); it.current(); ++it )
378
if ( it.current()->isDir() )
382
if (!it.current()->isLink()) // ignore symlinks
383
fileSizeSum += it.current()->size();
387
emit setStatusBarText( KIO::itemsSummaryString(fileCount + dirCount,
396
// Yes, the caller could do that too :)
397
// But this bool could also be used to cache the QString for the last
398
// selection, as long as selectionChanged is false.
399
// Not sure it's worth it though.
400
if ( selectionChanged )
401
emit m_extension->selectionInfo( lst );
404
void KonqDirPart::emitMouseOver( const KFileItem* item )
406
emit m_extension->mouseOverInfo( item );
409
void KonqDirPart::slotIconSizeToggled( bool )
411
//kdDebug(1203) << "KonqDirPart::slotIconSizeToggled" << endl;
412
if ( m_paDefaultIcons->isChecked() )
414
else if ( m_paHugeIcons->isChecked() )
415
setIconSize(m_iIconSize[4]);
416
else if ( m_paLargeIcons->isChecked() )
417
setIconSize(m_iIconSize[3]);
418
else if ( m_paMediumIcons->isChecked() )
419
setIconSize(m_iIconSize[2]);
420
else if ( m_paSmallIcons->isChecked() )
421
setIconSize(m_iIconSize[1]);
424
void KonqDirPart::slotIncIconSize()
426
int s = m_pProps->iconSize();
427
s = s ? s : KGlobal::iconLoader()->currentSize( KIcon::Desktop );
429
for ( int idx=1; idx < 5 ; ++idx )
430
if (s == m_iIconSize[idx])
432
if ( sizeIndex > 0 && sizeIndex < 4 )
434
setIconSize( m_iIconSize[sizeIndex + 1] );
438
void KonqDirPart::slotDecIconSize()
440
int s = m_pProps->iconSize();
441
s = s ? s : KGlobal::iconLoader()->currentSize( KIcon::Desktop );
443
for ( int idx=1; idx < 5 ; ++idx )
444
if (s == m_iIconSize[idx])
448
setIconSize( m_iIconSize[sizeIndex - 1] );
452
// Only updates the GUI (that's the one that is reimplemented by the views, too)
453
void KonqDirPart::newIconSize( int size /*0=default, or 16,32,48....*/ )
455
int realSize = (size==0) ? KGlobal::iconLoader()->currentSize( KIcon::Desktop ) : size;
456
m_paDecIconSize->setEnabled(realSize > m_iIconSize[1]);
457
m_paIncIconSize->setEnabled(realSize < m_iIconSize[4]);
459
m_paDefaultIcons->setChecked( size == 0 );
460
m_paHugeIcons->setChecked( size == m_iIconSize[4] );
461
m_paLargeIcons->setChecked( size == m_iIconSize[3] );
462
m_paMediumIcons->setChecked( size == m_iIconSize[2] );
463
m_paSmallIcons->setChecked( size == m_iIconSize[1] );
466
// Stores the new icon size and updates the GUI
467
void KonqDirPart::setIconSize( int size )
469
//kdDebug(1203) << "KonqDirPart::setIconSize " << size << " -> updating props and GUI" << endl;
470
m_pProps->setIconSize( size );
474
bool KonqDirPart::closeURL()
476
// Tell all the childern objects to clean themselves up for dinner :)
480
bool KonqDirPart::openURL(const KURL& url)
484
kdDebug(1203) << "KonqDirPart::openURL -> emit findClosed " << this << endl;
487
emit findClosed( this );
491
emit aboutToOpenURL ();
493
return doOpenURL(url);
496
void KonqDirPart::setFindPart( KParts::ReadOnlyPart * part )
500
connect( m_findPart, SIGNAL( started() ),
501
this, SLOT( slotStarted() ) );
502
connect( m_findPart, SIGNAL( started() ),
503
this, SLOT( slotStartAnimationSearching() ) );
504
connect( m_findPart, SIGNAL( clear() ),
505
this, SLOT( slotClear() ) );
506
connect( m_findPart, SIGNAL( newItems( const KFileItemList & ) ),
507
this, SLOT( slotNewItems( const KFileItemList & ) ) );
508
connect( m_findPart, SIGNAL( finished() ), // can't name it completed, it conflicts with a KROP signal
509
this, SLOT( slotCompleted() ) );
510
connect( m_findPart, SIGNAL( finished() ),
511
this, SLOT( slotStopAnimationSearching() ) );
512
connect( m_findPart, SIGNAL( canceled() ),
513
this, SLOT( slotCanceled() ) );
514
connect( m_findPart, SIGNAL( canceled() ),
515
this, SLOT( slotStopAnimationSearching() ) );
517
connect( m_findPart, SIGNAL( findClosed() ),
518
this, SLOT( slotFindClosed() ) );
520
emit findOpened( this );
522
// set the initial URL in the find part
523
m_findPart->openURL( url() );
526
void KonqDirPart::slotFindClosed()
528
kdDebug(1203) << "KonqDirPart::slotFindClosed -> emit findClosed " << this << endl;
531
emit findClosed( this );
532
// reload where we were before
536
void KonqDirPart::slotStartAnimationSearching()
541
void KonqDirPart::slotStopAnimationSearching()
546
void KonqDirPartBrowserExtension::saveState( QDataStream &stream )
548
m_dirPart->saveState( stream );
549
bool hasFindPart = m_dirPart->findPart();
550
stream << hasFindPart;
551
assert( ! ( hasFindPart && m_dirPart->className() == "KFindPart" ) );
553
KParts::BrowserExtension::saveState( stream );
555
m_dirPart->saveFindState( stream );
559
void KonqDirPartBrowserExtension::restoreState( QDataStream &stream )
561
m_dirPart->restoreState( stream );
563
stream >> hasFindPart;
564
assert( ! ( hasFindPart && m_dirPart->className() == "KFindPart" ) );
566
// This calls openURL, that's why we don't want to call it in case of a find part
567
KParts::BrowserExtension::restoreState( stream );
569
m_dirPart->restoreFindState( stream );
574
#include "konq_dirpart.moc"