]> cloud.milkyroute.net Git - dolphin.git/blob - src/panels/folders/treeviewcontextmenu.cpp
419d174e90ace364d9fc432534dbe8f64a43a69c
[dolphin.git] / src / panels / folders / treeviewcontextmenu.cpp
1 /*
2 * SPDX-FileCopyrightText: 2006-2010 Peter Penz <peter.penz19@gmail.com>
3 * SPDX-FileCopyrightText: 2006 Cvetoslav Ludmiloff <ludmiloff@gmail.com>
4 *
5 * SPDX-License-Identifier: GPL-2.0-or-later
6 */
7
8 #include "treeviewcontextmenu.h"
9
10 #include "folderspanel.h"
11 #include "global.h"
12
13 #include <KConfigGroup>
14 #include <KFileItemListProperties>
15 #include <KIO/CopyJob>
16 #include <KIO/DeleteOrTrashJob>
17 #include <KIO/Paste>
18 #include <KIO/PasteJob>
19 #include <KJobWidgets>
20 #include <KLocalizedString>
21 #include <KPropertiesDialog>
22 #include <KSharedConfig>
23 #include <KUrlMimeData>
24
25 #include <QApplication>
26 #include <QClipboard>
27 #include <QMenu>
28 #include <QMimeData>
29 #include <QPointer>
30
31 TreeViewContextMenu::TreeViewContextMenu(FoldersPanel *parent, const KFileItem &fileInfo)
32 : QObject(parent)
33 , m_parent(parent)
34 , m_fileItem(fileInfo)
35 {
36 }
37
38 TreeViewContextMenu::~TreeViewContextMenu()
39 {
40 }
41
42 void TreeViewContextMenu::open(const QPoint &pos)
43 {
44 QMenu *popup = new QMenu(m_parent);
45
46 if (!m_fileItem.isNull()) {
47 KFileItemListProperties capabilities(KFileItemList() << m_fileItem);
48
49 // insert 'Cut', 'Copy' and 'Paste'
50 QAction *cutAction = new QAction(QIcon::fromTheme(QStringLiteral("edit-cut")), i18nc("@action:inmenu", "Cut"), this);
51 cutAction->setEnabled(capabilities.supportsMoving());
52 connect(cutAction, &QAction::triggered, this, &TreeViewContextMenu::cut);
53
54 QAction *copyAction = new QAction(QIcon::fromTheme(QStringLiteral("edit-copy")), i18nc("@action:inmenu", "Copy"), this);
55 connect(copyAction, &QAction::triggered, this, &TreeViewContextMenu::copy);
56
57 const QMimeData *mimeData = QApplication::clipboard()->mimeData();
58 bool canPaste;
59 const QString text = KIO::pasteActionText(mimeData, &canPaste, m_fileItem);
60 QAction *pasteAction = new QAction(QIcon::fromTheme(QStringLiteral("edit-paste")), text, this);
61 connect(pasteAction, &QAction::triggered, this, &TreeViewContextMenu::paste);
62 pasteAction->setEnabled(canPaste);
63
64 popup->addAction(cutAction);
65 popup->addAction(copyAction);
66 popup->addAction(pasteAction);
67 popup->addSeparator();
68
69 // insert 'Rename'
70 QAction *renameAction = new QAction(i18nc("@action:inmenu", "Rename…"), this);
71 renameAction->setEnabled(capabilities.supportsMoving());
72 renameAction->setIcon(QIcon::fromTheme(QStringLiteral("edit-rename")));
73 connect(renameAction, &QAction::triggered, this, &TreeViewContextMenu::rename);
74 popup->addAction(renameAction);
75
76 // insert 'Move to Trash' and (optionally) 'Delete'
77 KSharedConfig::Ptr globalConfig = KSharedConfig::openConfig(QStringLiteral("kdeglobals"), KConfig::IncludeGlobals);
78 KConfigGroup configGroup(globalConfig, "KDE");
79 bool showDeleteCommand = configGroup.readEntry("ShowDeleteCommand", false);
80
81 const QUrl url = m_fileItem.url();
82 if (url.isLocalFile()) {
83 QAction *moveToTrashAction = new QAction(QIcon::fromTheme(QStringLiteral("user-trash")), i18nc("@action:inmenu", "Move to Trash"), this);
84 const bool enableMoveToTrash = capabilities.isLocal() && capabilities.supportsMoving();
85 moveToTrashAction->setEnabled(enableMoveToTrash);
86 connect(moveToTrashAction, &QAction::triggered, this, &TreeViewContextMenu::moveToTrash);
87 popup->addAction(moveToTrashAction);
88 } else {
89 showDeleteCommand = true;
90 }
91
92 if (showDeleteCommand) {
93 QAction *deleteAction = new QAction(QIcon::fromTheme(QStringLiteral("edit-delete")), i18nc("@action:inmenu", "Delete"), this);
94 deleteAction->setEnabled(capabilities.supportsDeleting());
95 connect(deleteAction, &QAction::triggered, this, &TreeViewContextMenu::deleteItem);
96 popup->addAction(deleteAction);
97 }
98
99 popup->addSeparator();
100 }
101
102 // insert 'Show Hidden Files'
103 QAction *showHiddenFilesAction = new QAction(i18nc("@action:inmenu", "Show Hidden Files"), this);
104 showHiddenFilesAction->setCheckable(true);
105 showHiddenFilesAction->setChecked(m_parent->showHiddenFiles());
106 popup->addAction(showHiddenFilesAction);
107 connect(showHiddenFilesAction, &QAction::toggled, this, &TreeViewContextMenu::setShowHiddenFiles);
108
109 if (!m_fileItem.isNull()) {
110 // insert 'Limit to Home Directory'
111 const QUrl url = m_fileItem.url();
112 const bool enableLimitToHomeDirectory = url.isLocalFile();
113 QAction *limitFoldersPanelToHomeAction = new QAction(i18nc("@action:inmenu", "Limit to Home Directory"), this);
114 limitFoldersPanelToHomeAction->setCheckable(true);
115 limitFoldersPanelToHomeAction->setEnabled(enableLimitToHomeDirectory);
116 limitFoldersPanelToHomeAction->setChecked(m_parent->limitFoldersPanelToHome());
117 popup->addAction(limitFoldersPanelToHomeAction);
118 connect(limitFoldersPanelToHomeAction, &QAction::toggled, this, &TreeViewContextMenu::setLimitFoldersPanelToHome);
119 }
120
121 // insert 'Automatic Scrolling'
122 QAction *autoScrollingAction = new QAction(i18nc("@action:inmenu", "Automatic Scrolling"), this);
123 autoScrollingAction->setCheckable(true);
124 autoScrollingAction->setChecked(m_parent->autoScrolling());
125 // TODO: Temporary disabled. Horizontal autoscrolling will be implemented later either
126 // in KItemViews or manually as part of the FoldersPanel
127 //popup->addAction(autoScrollingAction);
128 connect(autoScrollingAction, &QAction::toggled, this, &TreeViewContextMenu::setAutoScrolling);
129
130 if (!m_fileItem.isNull()) {
131 // insert 'Properties' entry
132 QAction *propertiesAction = new QAction(i18nc("@action:inmenu", "Properties"), this);
133 propertiesAction->setIcon(QIcon::fromTheme(QStringLiteral("document-properties")));
134 connect(propertiesAction, &QAction::triggered, this, &TreeViewContextMenu::showProperties);
135 popup->addAction(propertiesAction);
136 }
137
138 const QList<QAction *> customActions = m_parent->customContextMenuActions();
139 if (!customActions.isEmpty()) {
140 popup->addSeparator();
141 for (QAction *action : customActions) {
142 popup->addAction(action);
143 }
144 }
145
146 QPointer<QMenu> popupPtr = popup;
147 popup->exec(pos);
148 if (popupPtr.data()) {
149 popupPtr.data()->deleteLater();
150 }
151 }
152
153 void TreeViewContextMenu::populateMimeData(QMimeData *mimeData, bool cut)
154 {
155 QList<QUrl> kdeUrls;
156 kdeUrls.append(m_fileItem.url());
157 QList<QUrl> mostLocalUrls;
158 bool dummy;
159 mostLocalUrls.append(m_fileItem.mostLocalUrl(&dummy));
160 KIO::setClipboardDataCut(mimeData, cut);
161 KUrlMimeData::exportUrlsToPortal(mimeData);
162 KUrlMimeData::setUrls(kdeUrls, mostLocalUrls, mimeData);
163 }
164
165 void TreeViewContextMenu::cut()
166 {
167 QMimeData *mimeData = new QMimeData();
168 populateMimeData(mimeData, true);
169 QApplication::clipboard()->setMimeData(mimeData);
170 }
171
172 void TreeViewContextMenu::copy()
173 {
174 QMimeData *mimeData = new QMimeData();
175 populateMimeData(mimeData, false);
176 QApplication::clipboard()->setMimeData(mimeData);
177 }
178
179 void TreeViewContextMenu::paste()
180 {
181 KIO::PasteJob *job = KIO::paste(QApplication::clipboard()->mimeData(), m_fileItem.url());
182 KJobWidgets::setWindow(job, m_parent);
183 }
184
185 void TreeViewContextMenu::rename()
186 {
187 m_parent->rename(m_fileItem);
188 }
189
190 void TreeViewContextMenu::moveToTrash()
191 {
192 using Iface = KIO::AskUserActionInterface;
193 auto *deleteJob = new KIO::DeleteOrTrashJob(QList{m_fileItem.url()}, Iface::Trash, Iface::DefaultConfirmation, m_parent);
194 deleteJob->start();
195 }
196
197 void TreeViewContextMenu::deleteItem()
198 {
199 using Iface = KIO::AskUserActionInterface;
200 auto *deleteJob = new KIO::DeleteOrTrashJob(QList{m_fileItem.url()}, Iface::Delete, Iface::DefaultConfirmation, m_parent);
201 deleteJob->start();
202 }
203
204 void TreeViewContextMenu::showProperties()
205 {
206 KPropertiesDialog *dialog = new KPropertiesDialog(m_fileItem.url(), m_parent);
207 dialog->setAttribute(Qt::WA_DeleteOnClose);
208 dialog->show();
209 }
210
211 void TreeViewContextMenu::setShowHiddenFiles(bool show)
212 {
213 m_parent->setShowHiddenFiles(show);
214 }
215
216 void TreeViewContextMenu::setLimitFoldersPanelToHome(bool enable)
217 {
218 m_parent->setLimitFoldersPanelToHome(enable);
219 }
220
221 void TreeViewContextMenu::setAutoScrolling(bool enable)
222 {
223 m_parent->setAutoScrolling(enable);
224 }
225
226 #include "moc_treeviewcontextmenu.cpp"