From 405dd624fb6b708eea8ec82ef913fe820c51c654 Mon Sep 17 00:00:00 2001 From: Nathaniel Graham Date: Fri, 20 Dec 2019 10:07:25 -0700 Subject: Add Duplicate feature Summary: Adds a Duplicate feature to Dolphin, showing up as a menu item in the File menu that appears when one or more items are selected and the directory is writable. Duplicated items receive the names of the original files with " copy" appended before the file extension, if any. Test Plan: {F5201386} {F5201393} Test cases: - Try to duplicate when nothing is selected: **PASS**: menu item is grayed out - Try to duplicate anything on a read-only local volume: **PASS**: menu item is grayed out - Try to duplicate anything on a read-only samba share: **PASS**: menu item is grayed out - Duplicate single local file on R/W volume: **PASS**: item is duplicated and named correctly - Duplicate multiple local files on R/W volume: **PASS**: 3 items are duplicated, named correctly, and selected - Duplicate single local directory on R/W volume: **PASS**: item is duplicated and named correctly, but a rename operation is not initiated - Duplicate multiple local directories on R/W volume: **PASS**: 3 items are duplicated, named correctly, and selected - Duplicate single file on R/W samba share: **PASS**: item is duplicated and correctly - Duplicate multiple files on R/W samba share: **PASS**: 3 items are duplicated, named correctly, and selected - Duplicate single directory on R/W samba share: **PASS**: item is duplicated and named correctly - Duplicate multiple directory on R/W samba share: **PASS**: 3 items are duplicated, named correctly, and selected - Try to undo a successful duplication: **PASS**: operation is undone This is my first attempt at a big change like this and I'm sure it's full of issues. I will accept any and all suggestions for improvement. :) Reviewers: #dolphin, #kde_applications, elvisangelaccio, dfaure, broulik, davidedmundson Subscribers: kfm-devel, meven, markg, fazevedo, cfeck, #dolphin Tags: #dolphin Differential Revision: https://phabricator.kde.org/D8208 --- src/dolphinmainwindow.cpp | 2 ++ 1 file changed, 2 insertions(+) (limited to 'src/dolphinmainwindow.cpp') diff --git a/src/dolphinmainwindow.cpp b/src/dolphinmainwindow.cpp index 642c24e60..399901688 100644 --- a/src/dolphinmainwindow.cpp +++ b/src/dolphinmainwindow.cpp @@ -1905,6 +1905,7 @@ void DolphinMainWindow::updateFileAndEditActions() QAction* cutAction = col->action(KStandardAction::name(KStandardAction::Cut)); QAction* deleteWithTrashShortcut = col->action(QStringLiteral("delete_shortcut")); // see DolphinViewActionHandler QAction* showTarget = col->action(QStringLiteral("show_target")); + QAction* duplicateAction = col->action(QStringLiteral("duplicate")); // see DolphinViewActionHandler if (list.length() == 1 && list.first().isDir()) { addToPlacesAction->setEnabled(true); @@ -1921,6 +1922,7 @@ void DolphinMainWindow::updateFileAndEditActions() deleteWithTrashShortcut->setEnabled(capabilities.supportsDeleting() && !enableMoveToTrash); cutAction->setEnabled(capabilities.supportsMoving()); showTarget->setEnabled(list.length() == 1 && list.at(0).isLink()); + duplicateAction->setEnabled(capabilities.supportsWriting()); } } -- cgit v1.3 From 869b8d7e303b318d7370309d6caa82a0ba8056bf Mon Sep 17 00:00:00 2001 From: Elvis Angelaccio Date: Mon, 23 Dec 2019 11:06:54 +0100 Subject: Switch to generated MainWindow dbus interface Summary: This allows compile-time checks for the main window dbus methods. Test Plan: Same test plan as in D21691, D21666 and D25510. Reviewers: #dolphin Subscribers: kfm-devel Tags: #dolphin Differential Revision: https://phabricator.kde.org/D26214 --- src/CMakeLists.txt | 4 ++++ src/dolphinmainwindow.cpp | 4 ++++ src/global.cpp | 40 ++++++++++++++++++++++------------------ 3 files changed, 30 insertions(+), 18 deletions(-) (limited to 'src/dolphinmainwindow.cpp') diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index e8d623d2f..02a43a209 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -269,6 +269,10 @@ kconfig_add_kcfg_files(dolphinstatic_SRCS GENERATE_MOC qt5_add_resources(dolphinstatic_SRCS dolphin.qrc) +qt5_generate_dbus_interface(${CMAKE_CURRENT_SOURCE_DIR}/dolphinmainwindow.h org.kde.DolphinMainWindow.xml) +qt5_add_dbus_adaptor(dolphinstatic_SRCS ${CMAKE_CURRENT_BINARY_DIR}/org.kde.DolphinMainWindow.xml dolphinmainwindow.h DolphinMainWindow) +qt5_add_dbus_interface(dolphinstatic_SRCS ${CMAKE_CURRENT_BINARY_DIR}/org.kde.DolphinMainWindow.xml dolphinmainwindowinterface) + add_library(dolphinstatic STATIC ${dolphinstatic_SRCS}) target_include_directories(dolphinstatic SYSTEM PRIVATE ${PHONON_INCLUDES}) diff --git a/src/dolphinmainwindow.cpp b/src/dolphinmainwindow.cpp index 399901688..f88bc3f44 100644 --- a/src/dolphinmainwindow.cpp +++ b/src/dolphinmainwindow.cpp @@ -21,6 +21,7 @@ #include "dolphinmainwindow.h" +#include "dolphinmainwindowadaptor.h" #include "config-terminal.h" #include "global.h" #include "dolphinbookmarkhandler.h" @@ -118,6 +119,9 @@ DolphinMainWindow::DolphinMainWindow() : m_forwardAction(nullptr) { Q_INIT_RESOURCE(dolphin); + + new MainWindowAdaptor(this); + #ifndef Q_OS_WIN setWindowFlags(Qt::WindowContextHelpButtonHint); #endif diff --git a/src/global.cpp b/src/global.cpp index 34ed4e824..5236fa4d1 100644 --- a/src/global.cpp +++ b/src/global.cpp @@ -21,14 +21,13 @@ #include "dolphin_generalsettings.h" #include "dolphindebug.h" +#include "dolphinmainwindowinterface.h" #include #include #include #include -#include -#include QList Dolphin::validateUris(const QStringList& uriList) { @@ -72,18 +71,19 @@ void Dolphin::openNewWindow(const QList &urls, QWidget *window, const Open bool Dolphin::attachToExistingInstance(const QList& inputUrls, bool openFiles, bool splitView, const QString& preferredService) { + bool attached = false; + // TODO: once Wayland clients can raise or activate themselves remove check from conditional if (KWindowSystem::isPlatformWayland() || inputUrls.isEmpty() || !GeneralSettings::openExternallyCalledFolderInNewTab()) { return false; } - QVector, QStringList>> dolphinInterfaces; + QVector, QStringList>> dolphinInterfaces; if (!preferredService.isEmpty()) { - QSharedPointer preferredInterface( - new QDBusInterface(preferredService, - QStringLiteral("/dolphin/Dolphin_1"), - QStringLiteral("org.kde.dolphin.MainWindow")) - ); + QSharedPointer preferredInterface( + new OrgKdeDolphinMainWindowInterface(preferredService, + QStringLiteral("/dolphin/Dolphin_1"), + QDBusConnection::sessionBus())); if (preferredInterface->isValid() && !preferredInterface->lastError().isValid()) { dolphinInterfaces.append(qMakePair(preferredInterface, QStringList())); } @@ -98,11 +98,10 @@ bool Dolphin::attachToExistingInstance(const QList& inputUrls, bool openFi for (const QString& service : dbusServices) { if (service.startsWith(pattern) && !service.endsWith(myPid)) { // Check if instance can handle our URLs - QSharedPointer interface( - new QDBusInterface(service, - QStringLiteral("/dolphin/Dolphin_1"), - QStringLiteral("org.kde.dolphin.MainWindow")) - ); + QSharedPointer interface( + new OrgKdeDolphinMainWindowInterface(service, + QStringLiteral("/dolphin/Dolphin_1"), + QDBusConnection::sessionBus())); if (interface->isValid() && !interface->lastError().isValid()) { dolphinInterfaces.append(qMakePair(interface, QStringList())); } @@ -120,8 +119,9 @@ bool Dolphin::attachToExistingInstance(const QList& inputUrls, bool openFi for (const QString& url : urls) { bool urlFound = false; for (auto& interface: dolphinInterfaces) { - QDBusReply isUrlOpenReply = interface.first->call(QStringLiteral("isUrlOpen"), url); - if (isUrlOpenReply.isValid() && isUrlOpenReply.value()) { + auto isUrlOpenReply = interface.first->isUrlOpen(url); + isUrlOpenReply.waitForFinished(); + if (!isUrlOpenReply.isError() && isUrlOpenReply.value()) { interface.second.append(url); urlFound = true; break; @@ -135,9 +135,13 @@ bool Dolphin::attachToExistingInstance(const QList& inputUrls, bool openFi for (const auto& interface: dolphinInterfaces) { if (!interface.second.isEmpty()) { - interface.first->call(openFiles ? QStringLiteral("openFiles") : QStringLiteral("openDirectories"), interface.second, splitView); - interface.first->call(QStringLiteral("activateWindow")); + auto reply = openFiles ? interface.first->openFiles(interface.second, splitView) : interface.first->openDirectories(interface.second, splitView); + reply.waitForFinished(); + if (!reply.isError()) { + interface.first->activateWindow(); + attached = true; + } } } - return true; + return attached; } -- cgit v1.3