*/
#include "dolphinpart.h"
+#include "dolphinremoveaction.h"
#include <KFileItemListProperties>
#include <konq_operations.h>
-#include <kaboutdata.h>
+#include <KAboutData>
#include <KActionCollection>
#include <KConfigGroup>
#include <KDebug>
#include <KLocale>
#include <KMessageBox>
#include <KPluginFactory>
+#include <KRun>
#include <KToggleAction>
#include <KIO/NetAccess>
-#include <ktoolinvocation.h>
+#include <KToolInvocation>
#include <kauthorized.h>
-#include <knewfilemenu.h>
#include <KMenu>
-#include <kinputdialog.h>
+#include <KInputDialog>
#include <KProtocolInfo>
+#include <kdeversion.h>
-#include "settings/dolphinsettings.h"
+#if KDE_IS_VERSION(4, 9, 2)
+#include "dolphinpart_ext.h"
+#endif
+
+#include "dolphinnewfilemenu.h"
#include "views/dolphinview.h"
#include "views/dolphinviewactionhandler.h"
-#include "views/dolphinsortfilterproxymodel.h"
-#include "views/dolphinmodel.h"
#include "views/dolphinnewfilemenuobserver.h"
#include "views/dolphinremoteencoding.h"
-#include "views/dolphindirlister.h"
+#include "kitemviews/kfileitemmodel.h"
+#include "kitemviews/private/kfileitemmodeldirlister.h"
#include <QActionGroup>
#include <QApplication>
#include <QClipboard>
+#include <QDir>
+#include <QTextDocument>
K_PLUGIN_FACTORY(DolphinPartFactory, registerPlugin<DolphinPart>();)
K_EXPORT_PLUGIN(DolphinPartFactory("dolphinpart", "dolphin"))
DolphinPart::DolphinPart(QWidget* parentWidget, QObject* parent, const QVariantList& args)
: KParts::ReadOnlyPart(parent)
+ ,m_openTerminalAction(0)
+ ,m_removeAction(0)
{
Q_UNUSED(args)
setComponentData(DolphinPartFactory::componentData(), false);
m_extension = new DolphinPartBrowserExtension(this);
- new DolphinPartFileInfoExtension(this);
// make sure that other apps using this part find Dolphin's view-file-columns icons
KIconLoader::global()->addAppDir("dolphin");
m_view->setTabsForFilesEnabled(true);
setWidget(m_view);
- connect(m_view, SIGNAL(finishedPathLoading(KUrl)), this, SLOT(slotCompleted(KUrl)));
- connect(m_view, SIGNAL(pathLoadingProgress(int)), this, SLOT(updateProgress(int)));
+ connect(&DolphinNewFileMenuObserver::instance(), SIGNAL(errorMessage(QString)),
+ this, SLOT(slotErrorMessage(QString)));
+
+ connect(m_view, SIGNAL(directoryLoadingCompleted()), this, SIGNAL(completed()));
+ connect(m_view, SIGNAL(directoryLoadingProgress(int)), this, SLOT(updateProgress(int)));
connect(m_view, SIGNAL(errorMessage(QString)), this, SLOT(slotErrorMessage(QString)));
setXMLFile("dolphinpart.rc");
this, SLOT(slotMessage(QString)));
connect(m_view, SIGNAL(errorMessage(QString)),
this, SLOT(slotErrorMessage(QString)));
- connect(m_view, SIGNAL(itemTriggered(KFileItem)),
- this, SLOT(slotItemTriggered(KFileItem)));
+ connect(m_view, SIGNAL(itemActivated(KFileItem)),
+ this, SLOT(slotItemActivated(KFileItem)));
+ connect(m_view, SIGNAL(itemsActivated(KFileItemList)),
+ this, SLOT(slotItemsActivated(KFileItemList)));
connect(m_view, SIGNAL(tabRequested(KUrl)),
this, SLOT(createNewWindow(KUrl)));
- connect(m_view, SIGNAL(requestContextMenu(KFileItem,KUrl,QList<QAction*>)),
- this, SLOT(slotOpenContextMenu(KFileItem,KUrl,QList<QAction*>)));
+ connect(m_view, SIGNAL(requestContextMenu(QPoint,KFileItem,KUrl,QList<QAction*>)),
+ this, SLOT(slotOpenContextMenu(QPoint,KFileItem,KUrl,QList<QAction*>)));
connect(m_view, SIGNAL(selectionChanged(KFileItemList)),
m_extension, SIGNAL(selectionInfo(KFileItemList)));
connect(m_view, SIGNAL(selectionChanged(KFileItemList)),
this, SLOT(slotSelectionChanged(KFileItemList)));
connect(m_view, SIGNAL(requestItemInfo(KFileItem)),
this, SLOT(slotRequestItemInfo(KFileItem)));
- connect(m_view, SIGNAL(modeChanged()),
+ connect(m_view, SIGNAL(modeChanged(DolphinView::Mode,DolphinView::Mode)),
this, SIGNAL(viewModeChanged())); // relay signal
- connect(m_view, SIGNAL(redirection(KUrl, KUrl)),
- this, SLOT(slotRedirection(KUrl, KUrl)));
+ connect(m_view, SIGNAL(redirection(KUrl,KUrl)),
+ this, SLOT(slotDirectoryRedirection(KUrl,KUrl)));
// Watch for changes that should result in updates to the
// status bar text.
connect(m_view, SIGNAL(itemCountChanged()), this, SLOT(updateStatusBar()));
- connect(m_view, SIGNAL(selectionChanged(const KFileItemList)), this, SLOT(updateStatusBar()));
+ connect(m_view, SIGNAL(selectionChanged(KFileItemList)), this, SLOT(updateStatusBar()));
m_actionHandler = new DolphinViewActionHandler(actionCollection(), this);
m_actionHandler->setCurrentView(m_view);
connect(clipboard, SIGNAL(dataChanged()),
this, SLOT(updatePasteAction()));
+ // Create file info and listing filter extensions.
+ // NOTE: Listing filter needs to be instantiated after the creation of the view.
+ new DolphinPartFileInfoExtension(this);
+
+#if KDE_IS_VERSION(4, 9, 2)
+ new DolphinPartListingFilterExtension(this);
+
+ KDirLister* lister = m_view->m_model->m_dirLister;
+ if (lister) {
+ DolphinPartListingNotificationExtension* notifyExt = new DolphinPartListingNotificationExtension(this);
+ connect(lister, SIGNAL(newItems(KFileItemList)), notifyExt, SLOT(slotNewItems(KFileItemList)));
+ connect(lister, SIGNAL(itemsDeleted(KFileItemList)), notifyExt, SLOT(slotItemsDeleted(KFileItemList)));
+ } else {
+ kWarning() << "NULL KDirLister object! KParts::ListingNotificationExtension will NOT be supported";
+ }
+#endif
+
createActions();
m_actionHandler->updateViewActions();
slotSelectionChanged(KFileItemList()); // initially disable selection-dependent actions
+ // Listen to events from the app so we can update the remove key by
+ // checking for a Shift key press.
+ qApp->installEventFilter(this);
+
// TODO there was a "always open a new window" (when clicking on a directory) setting in konqueror
// (sort of spacial navigation)
loadPlugins(this, this, componentData());
-
}
DolphinPart::~DolphinPart()
{
- DolphinSettings::instance().save();
- DolphinNewFileMenuObserver::instance().detach(m_newFileMenu);
}
void DolphinPart::createActions()
{
// Edit menu
- m_newFileMenu = new KNewFileMenu(actionCollection(), "new_menu", this);
+ m_newFileMenu = new DolphinNewFileMenu(actionCollection(), this);
m_newFileMenu->setParentWidget(widget());
- DolphinNewFileMenuObserver::instance().attach(m_newFileMenu);
connect(m_newFileMenu->menu(), SIGNAL(aboutToShow()),
this, SLOT(updateNewMenu()));
goActionGroup);
// Tools menu
+ m_findFileAction = actionCollection()->addAction("find_file");
+ m_findFileAction->setText(i18nc("@action:inmenu Tools", "Find File..."));
+ m_findFileAction->setShortcut(Qt::CTRL | Qt::Key_F);
+ m_findFileAction->setIcon(KIcon("edit-find"));
+ connect(m_findFileAction, SIGNAL(triggered()), this, SLOT(slotFindFile()));
+
if (KAuthorized::authorizeKAction("shell_access")) {
- KAction* action = actionCollection()->addAction("open_terminal");
- action->setIcon(KIcon("utilities-terminal"));
- action->setText(i18nc("@action:inmenu Tools", "Open &Terminal"));
- connect(action, SIGNAL(triggered()), SLOT(slotOpenTerminal()));
- action->setShortcut(Qt::Key_F4);
+ m_openTerminalAction = actionCollection()->addAction("open_terminal");
+ m_openTerminalAction->setIcon(KIcon("utilities-terminal"));
+ m_openTerminalAction->setText(i18nc("@action:inmenu Tools", "Open &Terminal"));
+ connect(m_openTerminalAction, SIGNAL(triggered()), SLOT(slotOpenTerminal()));
+ m_openTerminalAction->setShortcut(Qt::Key_F4);
}
-
}
void DolphinPart::createGoAction(const char* name, const char* iconName,
emit aboutToOpenURL();
if (reload)
m_view->reload();
+ // Disable "Find File" and "Open Terminal" actions for non-file URLs,
+ // e.g. ftp, smb, etc. #279283
+ const bool isLocalUrl = url.isLocalFile();
+ m_findFileAction->setEnabled(isLocalUrl);
+ if (m_openTerminalAction) {
+ m_openTerminalAction->setEnabled(isLocalUrl);
+ }
return true;
}
-void DolphinPart::slotCompleted(const KUrl& url)
-{
- Q_UNUSED(url)
- emit completed();
-}
-
void DolphinPart::slotMessage(const QString& msg)
{
emit setStatusBarText(msg);
if (item.isNull()) {
updateStatusBar();
} else {
- ReadOnlyPart::setStatusBarText(item.getStatusBarInfo());
+ const QString escapedText = Qt::convertFromPlainText(item.getStatusBarInfo());
+ ReadOnlyPart::setStatusBarText(QString("<qt>%1</qt>").arg(escapedText));
}
}
-void DolphinPart::slotItemTriggered(const KFileItem& item)
+void DolphinPart::slotItemActivated(const KFileItem& item)
{
KParts::OpenUrlArguments args;
// Forget about the known mimetype if a target URL is used.
emit m_extension->openUrlRequest(item.targetUrl(), args, browserArgs);
}
+void DolphinPart::slotItemsActivated(const KFileItemList& items)
+{
+ foreach (const KFileItem& item, items) {
+ slotItemActivated(item);
+ }
+}
+
void DolphinPart::createNewWindow(const KUrl& url)
{
// TODO: Check issue N176832 for the missing QAIV signal; task 177399 - maybe this code
- // should be moved into DolphinPart::slotItemTriggered()
+ // should be moved into DolphinPart::slotItemActivated()
emit m_extension->createNewWindow(url);
}
-void DolphinPart::slotOpenContextMenu(const KFileItem& _item,
+void DolphinPart::slotOpenContextMenu(const QPoint& pos,
+ const KFileItem& _item,
const KUrl&,
const QList<QAction*>& customActions)
{
editActions += customActions;
if (!_item.isNull()) { // only for context menu on one or more items
- bool supportsDeleting = capabilities.supportsDeleting();
- bool supportsMoving = capabilities.supportsMoving();
-
- if (!supportsDeleting) {
+ const bool supportsMoving = capabilities.supportsMoving();
+
+ if (capabilities.supportsDeleting()) {
+ const bool showDeleteAction = (KGlobal::config()->group("KDE").readEntry("ShowDeleteCommand", false) ||
+ !item.isLocalFile());
+ const bool showMoveToTrashAction = capabilities.isLocal() && supportsMoving;
+
+ if (showDeleteAction && showMoveToTrashAction) {
+ delete m_removeAction;
+ m_removeAction = 0;
+ editActions.append(actionCollection()->action("move_to_trash"));
+ editActions.append(actionCollection()->action("delete"));
+ } else if (showDeleteAction && !showMoveToTrashAction) {
+ editActions.append(actionCollection()->action("delete"));
+ } else {
+ if (!m_removeAction)
+ m_removeAction = new DolphinRemoveAction(this, actionCollection());
+ editActions.append(m_removeAction);
+ m_removeAction->update();
+ }
+ } else {
popupFlags |= KParts::BrowserExtension::NoDeletion;
}
editActions.append(actionCollection()->action("rename"));
}
- bool addTrash = capabilities.isLocal() && supportsMoving;
- bool addDel = false;
- if (supportsDeleting) {
- if ( !item.isLocalFile() )
- addDel = true;
- else if (QApplication::keyboardModifiers() & Qt::ShiftModifier) {
- addTrash = false;
- addDel = true;
- }
- else {
- KSharedConfig::Ptr globalConfig = KSharedConfig::openConfig("kdeglobals", KConfig::IncludeGlobals);
- KConfigGroup configGroup(globalConfig, "KDE");
- addDel = configGroup.readEntry("ShowDeleteCommand", false);
- }
- }
-
- if (addTrash)
- editActions.append(actionCollection()->action("move_to_trash"));
- if (addDel)
- editActions.append(actionCollection()->action("delete"));
-
// Normally KonqPopupMenu only shows the "Create new" submenu in the current view
// since otherwise the created file would not be visible.
// But in treeview mode we should allow it.
actionGroups.insert("editactions", editActions);
- emit m_extension->popupMenu(QCursor::pos(),
+ emit m_extension->popupMenu(pos,
items,
KParts::OpenUrlArguments(),
KParts::BrowserArguments(),
actionGroups);
}
-void DolphinPart::slotRedirection(const KUrl& oldUrl, const KUrl& newUrl)
+void DolphinPart::slotDirectoryRedirection(const KUrl& oldUrl, const KUrl& newUrl)
{
//kDebug() << oldUrl << newUrl << "currentUrl=" << url();
if (oldUrl.equals(url(), KUrl::CompareWithoutTrailingSlash /* #207572 */)) {
if (okClicked && !pattern.isEmpty()) {
QRegExp patternRegExp(pattern, Qt::CaseSensitive, QRegExp::Wildcard);
- m_view->setItemSelectionEnabled(patternRegExp, selectItems);
+ m_view->selectItems(patternRegExp, selectItems);
}
}
KToolInvocation::invokeTerminal(QString(), dir);
}
+void DolphinPart::slotFindFile()
+{
+ KRun::run("kfind", url(), widget());
+}
+
void DolphinPart::updateNewMenu()
{
// As requested by KNewFileMenu :
m_newFileMenu->checkUpToDate();
- m_newFileMenu->setViewShowsHiddenFiles(m_view->showHiddenFiles());
+ m_newFileMenu->setViewShowsHiddenFiles(m_view->hiddenFilesShown());
// And set the files that the menu apply on :
m_newFileMenu->setPopupFiles(url());
}
void DolphinPart::updateStatusBar()
{
- emit ReadOnlyPart::setStatusBarText(m_view->statusBarText());
+ const QString escapedText = Qt::convertFromPlainText(m_view->statusBarText());
+ emit ReadOnlyPart::setStatusBarText(QString("<qt>%1</qt>").arg(escapedText));
}
void DolphinPart::updateProgress(int percent)
void DolphinPart::createDirectory()
{
- m_newFileMenu->setViewShowsHiddenFiles(m_view->showHiddenFiles());
+ m_newFileMenu->setViewShowsHiddenFiles(m_view->hiddenFilesShown());
m_newFileMenu->setPopupFiles(url());
m_newFileMenu->createDirectory();
}
void DolphinPart::setFilesToSelect(const KUrl::List& files)
{
- m_view->markUrlsAsSelected(files);
-}
-
-////
-
-void DolphinPartBrowserExtension::restoreState(QDataStream &stream)
-{
- KParts::BrowserExtension::restoreState(stream);
- m_part->view()->restoreState(stream);
-}
-
-void DolphinPartBrowserExtension::saveState(QDataStream &stream)
-{
- KParts::BrowserExtension::saveState(stream);
- m_part->view()->saveState(stream);
-}
-
-void DolphinPartBrowserExtension::cut()
-{
- m_part->view()->cutSelectedItems();
-}
-
-void DolphinPartBrowserExtension::copy()
-{
- m_part->view()->copySelectedItems();
-}
-
-void DolphinPartBrowserExtension::paste()
-{
- m_part->view()->paste();
-}
-
-void DolphinPartBrowserExtension::pasteTo(const KUrl&)
-{
- m_part->view()->pasteIntoFolder();
-}
-
-void DolphinPartBrowserExtension::reparseConfiguration()
-{
- m_part->view()->refresh();
-}
-
-////
-
-DolphinPartFileInfoExtension::DolphinPartFileInfoExtension(DolphinPart* part)
- : KParts::FileInfoExtension(part)
-{
-}
-
-DolphinPart* DolphinPartFileInfoExtension::part() const
-{
- return static_cast<DolphinPart*>(parent());
-}
-
-bool DolphinPartFileInfoExtension::hasSelection() const
-{
- return part()->view()->hasSelection();
-}
+ if (files.isEmpty()) {
+ return;
+ }
-KParts::FileInfoExtension::QueryModes DolphinPartFileInfoExtension::supportedQueryModes() const
-{
- return (KParts::FileInfoExtension::AllItems | KParts::FileInfoExtension::SelectedItems);
+ m_view->markUrlsAsSelected(files);
+ m_view->markUrlAsCurrent(files.at(0));
}
-KFileItemList DolphinPartFileInfoExtension::queryFor(KParts::FileInfoExtension::QueryMode mode) const
+bool DolphinPart::eventFilter(QObject* obj, QEvent* event)
{
- KFileItemList list;
+ const int type = event->type();
- if (mode == KParts::FileInfoExtension::None)
- return list;
-
- if (!(supportedQueryModes() & mode))
- return list;
-
- switch (mode) {
- case KParts::FileInfoExtension::SelectedItems:
- if (hasSelection())
- return part()->view()->selectedItems();
- break;
- case KParts::FileInfoExtension::AllItems:
- return part()->view()->items();
- default:
- break;
+ if ((type == QEvent::KeyPress || type == QEvent::KeyRelease) && m_removeAction) {
+ QMenu* menu = qobject_cast<QMenu*>(obj);
+ if (menu && menu->parent() == m_view) {
+ QKeyEvent* ev = static_cast<QKeyEvent*>(event);
+ if (ev->key() == Qt::Key_Shift) {
+ m_removeAction->update();
+ }
+ }
}
- return list;
+ return KParts::ReadOnlyPart::eventFilter(obj, event);
}
#include "dolphinpart.moc"