diff options
| -rw-r--r-- | src/dolphinmainwindow.cpp | 375 | ||||
| -rw-r--r-- | src/dolphinmainwindow.h | 18 | ||||
| -rw-r--r-- | src/dolphinviewcontainer.cpp | 24 | ||||
| -rw-r--r-- | src/statusbar/dolphinstatusbar.cpp | 9 | ||||
| -rw-r--r-- | src/views/dolphinviewactionhandler.cpp | 58 | ||||
| -rw-r--r-- | src/views/dolphinviewactionhandler.h | 2 |
6 files changed, 473 insertions, 13 deletions
diff --git a/src/dolphinmainwindow.cpp b/src/dolphinmainwindow.cpp index c839e2d5c..ae139d363 100644 --- a/src/dolphinmainwindow.cpp +++ b/src/dolphinmainwindow.cpp @@ -72,6 +72,7 @@ #include <QApplication> #include <QClipboard> #include <QCloseEvent> +#include <QDesktopServices> #include <QDialog> #include <QFileInfo> #include <QLineEdit> @@ -82,6 +83,7 @@ #include <QStandardPaths> #include <QTimer> #include <QToolButton> +#include <QWhatsThisClickedEvent> namespace { // Used for GeneralSettings::version() to determine whether @@ -90,8 +92,9 @@ namespace { } DolphinMainWindow::DolphinMainWindow() : - KXmlGuiWindow(nullptr), + KXmlGuiWindow(nullptr, Qt::WindowContextHelpButtonHint), m_newFileMenu(nullptr), + m_helpMenu(nullptr), m_tabWidget(nullptr), m_activeViewContainer(nullptr), m_actionHandler(nullptr), @@ -181,6 +184,8 @@ DolphinMainWindow::DolphinMainWindow() : auto *middleClickEventFilter = new MiddleClickActionEventFilter(this); connect(middleClickEventFilter, &MiddleClickActionEventFilter::actionMiddleClicked, this, &DolphinMainWindow::slotToolBarActionMiddleClicked); toolBar()->installEventFilter(middleClickEventFilter); + + setupWhatsThis(); } DolphinMainWindow::~DolphinMainWindow() @@ -318,12 +323,15 @@ void DolphinMainWindow::updateHistory() QAction* backAction = actionCollection()->action(KStandardAction::name(KStandardAction::Back)); if (backAction) { backAction->setToolTip(i18nc("@info", "Go back")); + backAction->setWhatsThis(i18nc("@info:whatsthis go back", "Return to the previously viewed folder.")); backAction->setEnabled(index < urlNavigator->historySize() - 1); } QAction* forwardAction = actionCollection()->action(KStandardAction::name(KStandardAction::Forward)); if (forwardAction) { forwardAction->setToolTip(i18nc("@info", "Go forward")); + forwardAction->setWhatsThis(xi18nc("@info:whatsthis go forward", + "This undoes a <interface>Go|Back</interface> action.")); forwardAction->setEnabled(index > 0); } } @@ -1031,8 +1039,7 @@ void DolphinMainWindow::updateControlMenu() addActionToMenu(ac->action(KStandardAction::name(KStandardAction::Preferences)), menu); // Add "Help" menu - auto helpMenu = new KHelpMenu(menu); - menu->addMenu(helpMenu->menu()); + menu->addMenu(m_helpMenu->menu()); menu->addSeparator(); addActionToMenu(ac->action(KStandardAction::name(KStandardAction::ShowMenubar)), menu); @@ -1149,40 +1156,82 @@ void DolphinMainWindow::setupActions() QAction* newWindow = KStandardAction::openNew(this, &DolphinMainWindow::openNewMainWindow, actionCollection()); newWindow->setText(i18nc("@action:inmenu File", "New &Window")); + newWindow->setWhatsThis(xi18nc("@info:whatsthis", "This opens a new " + "window just like this one with the current location and view." + "<nl/>You can drag and drop items between windows.")); newWindow->setIcon(QIcon::fromTheme(QStringLiteral("window-new"))); QAction* newTab = actionCollection()->addAction(QStringLiteral("new_tab")); newTab->setIcon(QIcon::fromTheme(QStringLiteral("tab-new"))); newTab->setText(i18nc("@action:inmenu File", "New Tab")); + newTab->setWhatsThis(xi18nc("@info:whatsthis", "This opens a new " + "<emphasis>Tab</emphasis> with the current location and view.<nl/>" + "A tab is an additional view within this window. " + "You can drag and drop items between tabs.")); actionCollection()->setDefaultShortcuts(newTab, {Qt::CTRL + Qt::Key_T, Qt::CTRL + Qt::SHIFT + Qt::Key_N}); connect(newTab, &QAction::triggered, this, &DolphinMainWindow::openNewActivatedTab); QAction* closeTab = KStandardAction::close(m_tabWidget, QOverload<>::of(&DolphinTabWidget::closeTab), actionCollection()); closeTab->setText(i18nc("@action:inmenu File", "Close Tab")); + closeTab->setWhatsThis(i18nc("@info:whatsthis", "This closes the " + "currently viewed tab. If no more tabs are left this window " + "will close instead.")); - KStandardAction::quit(this, &DolphinMainWindow::quit, actionCollection()); + QAction* quitAction = KStandardAction::quit(this, &DolphinMainWindow::quit, actionCollection()); + quitAction->setWhatsThis(i18nc("@info:whatsthis quit", "This closes this window.")); // setup 'Edit' menu KStandardAction::undo(this, &DolphinMainWindow::undo, actionCollection()); - - KStandardAction::cut(this, &DolphinMainWindow::cut, actionCollection()); - KStandardAction::copy(this, &DolphinMainWindow::copy, actionCollection()); + // i18n: This will be the last paragraph for the whatsthis for all three: + // Cut, Copy and Paste + const QString cutCopyPastePara = xi18nc("@info:whatsthis", "<para><emphasis>Cut, " + "Copy</emphasis> and <emphasis>Paste</emphasis> work between many " + "applications and are among the most used commands. That's why their " + "<emphasis>keyboard shortcuts</emphasis> are prominently placed right " + "next to each other on the keyboard: <shortcut>Ctrl+X</shortcut>, " + "<shortcut>Ctrl+C</shortcut> and <shortcut>Ctrl+V</shortcut>.</para>"); + QAction* cutAction = KStandardAction::cut(this, &DolphinMainWindow::cut, actionCollection()); + cutAction->setWhatsThis(xi18nc("@info:whatsthis cut", "This copies the items " + "in your current selection to the <emphasis>clipboard</emphasis>.<nl/>" + "Use the <emphasis>Paste</emphasis> action afterwards to copy them from " + "the clipboard to a new location. The items will be removed from their " + "initial location.") + cutCopyPastePara); + QAction* copyAction = KStandardAction::copy(this, &DolphinMainWindow::copy, actionCollection()); + copyAction->setWhatsThis(xi18nc("@info:whatsthis copy", "This copies the " + "items in your current selection to the <emphasis>clipboard</emphasis>." + "<nl/>Use the <emphasis>Paste</emphasis> action afterwards to copy them " + "from the clipboard to a new location.") + cutCopyPastePara); QAction* paste = KStandardAction::paste(this, &DolphinMainWindow::paste, actionCollection()); // The text of the paste-action is modified dynamically by Dolphin // (e. g. to "Paste One Folder"). To prevent that the size of the toolbar changes // due to the long text, the text "Paste" is used: paste->setIconText(i18nc("@action:inmenu Edit", "Paste")); + paste->setWhatsThis(xi18nc("@info:whatsthis paste", "This copies the items from " + "your <emphasis>clipboard</emphasis> to the currently viewed folder.<nl/>" + "If the items were added to the clipboard by the <emphasis>Cut</emphasis> " + "action they are removed from their old location.") + cutCopyPastePara); QAction *searchAction = KStandardAction::find(this, &DolphinMainWindow::find, actionCollection()); searchAction->setText(i18n("Search...")); + searchAction->setToolTip(i18nc("@info:tooltip", "Search for files and folders")); + searchAction->setWhatsThis(xi18nc("@info:whatsthis find", "<para>This helps you " + "find files and folders by opening a <emphasis>find bar</emphasis>. " + "There you can enter search terms and specify settings to find the " + "objects you are looking for.</para><para>Use this help again on " + "the find bar so we can have a look at it while the settings are " + "explained.</para>")); - KStandardAction::selectAll(this, &DolphinMainWindow::selectAll, actionCollection()); + QAction* selectAllAction = KStandardAction::selectAll(this, &DolphinMainWindow::selectAll, actionCollection()); + selectAllAction->setWhatsThis(xi18nc("@info:whatsthis", "This selects all " + "files and folders in the current location.")); QAction* invertSelection = actionCollection()->addAction(QStringLiteral("invert_selection")); invertSelection->setText(i18nc("@action:inmenu Edit", "Invert Selection")); + invertSelection->setWhatsThis(xi18nc("@info:whatsthis invert", "This selects all " + "objects that you have currently <emphasis>not</emphasis> selected instead.")); invertSelection->setIcon(QIcon::fromTheme(QStringLiteral("edit-select-invert"))); actionCollection()->setDefaultShortcut(invertSelection, Qt::CTRL + Qt::SHIFT + Qt::Key_A); connect(invertSelection, &QAction::triggered, this, &DolphinMainWindow::invertSelection); @@ -1191,6 +1240,10 @@ void DolphinMainWindow::setupActions() // (note that most of it is set up in DolphinViewActionHandler) QAction* split = actionCollection()->addAction(QStringLiteral("split_view")); + split->setWhatsThis(xi18nc("@info:whatsthis find", "<para>This splits " + "the folder view below into two autonomous views.</para><para>This " + "way you can see two locations at once and move items between them " + "quickly.</para>Click this again afterwards to recombine the views.")); actionCollection()->setDefaultShortcut(split, Qt::Key_F3); connect(split, &QAction::triggered, this, &DolphinMainWindow::toggleSplitView); @@ -1208,16 +1261,28 @@ void DolphinMainWindow::setupActions() QAction* stop = actionCollection()->addAction(QStringLiteral("stop")); stop->setText(i18nc("@action:inmenu View", "Stop")); stop->setToolTip(i18nc("@info", "Stop loading")); + stop->setWhatsThis(i18nc("@info", "This stops the loading of the contents of the current folder.")); stop->setIcon(QIcon::fromTheme(QStringLiteral("process-stop"))); connect(stop, &QAction::triggered, this, &DolphinMainWindow::stopLoading); KToggleAction* editableLocation = actionCollection()->add<KToggleAction>(QStringLiteral("editable_location")); editableLocation->setText(i18nc("@action:inmenu Navigation Bar", "Editable Location")); + editableLocation->setWhatsThis(xi18nc("@info:whatsthis", + "This toggles the <emphasis>Location Bar</emphasis> to be " + "editable so you can directly enter a location you want to go to.<nl/>" + "You can also switch to editing by clicking to the right of the " + "location and switch back by confirming the edited location.")); actionCollection()->setDefaultShortcut(editableLocation, Qt::Key_F6); connect(editableLocation, &KToggleAction::triggered, this, &DolphinMainWindow::toggleEditLocation); QAction* replaceLocation = actionCollection()->addAction(QStringLiteral("replace_location")); replaceLocation->setText(i18nc("@action:inmenu Navigation Bar", "Replace Location")); + // i18n: "enter" is used both in the meaning of "writing" and "going to" a new location here. + // Both meanings are useful but not necessary to understand the use of "Replace Location". + // So you might want to be more verbose in your language to convey the meaning but it's up to you. + replaceLocation->setWhatsThis(xi18nc("@info:whatsthis", + "This switches to editing the location and selects it " + "so you can quickly enter a different location.")); actionCollection()->setDefaultShortcut(replaceLocation, Qt::CTRL + Qt::Key_L); connect(replaceLocation, &QAction::triggered, this, &DolphinMainWindow::replaceLocation); @@ -1238,21 +1303,37 @@ void DolphinMainWindow::setupActions() QAction* undoCloseTab = actionCollection()->addAction(QStringLiteral("undo_close_tab")); undoCloseTab->setText(i18nc("@action:inmenu File", "Undo close tab")); + undoCloseTab->setWhatsThis(i18nc("@info:whatsthis undo close tab", + "This returns you to the previously closed tab.")); actionCollection()->setDefaultShortcut(undoCloseTab, Qt::CTRL + Qt::SHIFT + Qt::Key_T); undoCloseTab->setIcon(QIcon::fromTheme(QStringLiteral("edit-undo"))); undoCloseTab->setEnabled(false); connect(undoCloseTab, &QAction::triggered, recentTabsMenu, &DolphinRecentTabsMenu::undoCloseTab); auto undoAction = actionCollection()->action(KStandardAction::name(KStandardAction::Undo)); + undoAction->setWhatsThis(xi18nc("@info:whatsthis", "This undoes " + "the last change you made to files or folders.<nl/>" + "Such changes include <interface>creating, renaming</interface> " + "and <interface>moving</interface> them to a different location " + "or to the <filename>Trash</filename>. <nl/>Changes that can't " + "be undone will ask for your confirmation.")); undoAction->setEnabled(false); // undo should be disabled by default KStandardAction::forward(this, &DolphinMainWindow::goForward, actionCollection()); KStandardAction::up(this, &DolphinMainWindow::goUp, actionCollection()); - KStandardAction::home(this, &DolphinMainWindow::goHome, actionCollection()); + QAction* homeAction = KStandardAction::home(this, &DolphinMainWindow::goHome, actionCollection()); + homeAction->setWhatsThis(xi18nc("@info:whatsthis", "Go to your " + "<filename>Home</filename> folder.<nl/>Every user account " + "has their own <filename>Home</filename> that contains their data " + "including folders that contain personal application data.")); // setup 'Tools' menu QAction* showFilterBar = actionCollection()->addAction(QStringLiteral("show_filter_bar")); showFilterBar->setText(i18nc("@action:inmenu Tools", "Show Filter Bar")); + showFilterBar->setWhatsThis(xi18nc("@info:whatsthis", "This opens the " + "<emphasis>Filter Bar</emphasis> at the bottom of the window.<nl/> " + "There you can enter a text to filter the files and folders currently displayed. " + "Only those that contain the text in their name will be kept in view.")); showFilterBar->setIcon(QIcon::fromTheme(QStringLiteral("view-filter"))); actionCollection()->setDefaultShortcuts(showFilterBar, {Qt::CTRL + Qt::Key_I, Qt::Key_Slash}); connect(showFilterBar, &QAction::triggered, this, &DolphinMainWindow::showFilterBar); @@ -1267,6 +1348,9 @@ void DolphinMainWindow::setupActions() if (KAuthorized::authorize(QStringLiteral("shell_access"))) { QAction* openTerminal = actionCollection()->addAction(QStringLiteral("open_terminal")); openTerminal->setText(i18nc("@action:inmenu Tools", "Open Terminal")); + openTerminal->setWhatsThis(xi18nc("@info:whatsthis", + "<para>This opens a <emphasis>terminal</emphasis> application for the viewed location.</para>" + "<para>To learn more about terminals use the help in the terminal application.</para>")); openTerminal->setIcon(QIcon::fromTheme(QStringLiteral("utilities-terminal"))); actionCollection()->setDefaultShortcut(openTerminal, Qt::SHIFT + Qt::Key_F4); connect(openTerminal, &QAction::triggered, this, &DolphinMainWindow::openTerminal); @@ -1283,10 +1367,21 @@ void DolphinMainWindow::setupActions() // setup 'Settings' menu KToggleAction* showMenuBar = KStandardAction::showMenubar(nullptr, nullptr, actionCollection()); + showMenuBar->setWhatsThis(xi18nc("@info:whatsthis", + "This switches between having a <emphasis>Menubar</emphasis> " + "and having a <interface>Control</interface> button. Both " + "contain mostly the same commands and configuration options.")); connect(showMenuBar, &KToggleAction::triggered, // Fixes #286822 this, &DolphinMainWindow::toggleShowMenuBar, Qt::QueuedConnection); KStandardAction::preferences(this, &DolphinMainWindow::editSettings, actionCollection()); + // setup 'Help' menu for the m_controlButton. The other one is set up in the base class. + m_helpMenu = new KHelpMenu(nullptr); + m_helpMenu->menu()->installEventFilter(this); + // remove duplicate shortcuts + m_helpMenu->action(KHelpMenu::menuHelpContents)->setShortcut(QKeySequence()); + m_helpMenu->action(KHelpMenu::menuWhatsThis)->setShortcut(QKeySequence()); + // not in menu actions QList<QKeySequence> nextTabKeys = KStandardShortcut::tabNext(); nextTabKeys.append(QKeySequence(Qt::CTRL + Qt::Key_Tab)); @@ -1340,6 +1435,11 @@ void DolphinMainWindow::setupDockWidgets() lockLayoutAction->setActiveIcon(QIcon::fromTheme(QStringLiteral("object-unlocked"))); lockLayoutAction->setInactiveText(i18nc("@action:inmenu Panels", "Lock Panels")); lockLayoutAction->setInactiveIcon(QIcon::fromTheme(QStringLiteral("object-locked"))); + lockLayoutAction->setWhatsThis(xi18nc("@info:whatsthis", "This " + "switches between having panels <emphasis>locked</emphasis> or " + "<emphasis>unlocked</emphasis>.<nl/>Unlocked panels can be " + "dragged to the other side of the window and have a close " + "button.<nl/>Locked panels are embedded more cleanly.")); lockLayoutAction->setActive(lock); connect(lockLayoutAction, &KDualAction::triggered, this, &DolphinMainWindow::togglePanelLockState); @@ -1367,6 +1467,24 @@ void DolphinMainWindow::setupDockWidgets() infoPanel, &InformationPanel::requestDelayedItemInfo); #endif + // i18n: This is the last paragraph for the "What's This"-texts of all four panels. + const QString panelWhatsThis = xi18nc("@info:whatsthis", "<para>To show or " + "hide panels like this go to <interface>Control|Panels</interface> " + "or <interface>View|Panels</interface>.</para>"); + actionCollection()->action(QStringLiteral("show_information_panel")) + ->setWhatsThis(xi18nc("@info:whatsthis", "<para> This toggles the " + "<emphasis>information</emphasis> panel at the right side of the " + "window.</para><para>The panel provides in-depth information " + "about the items your mouse is hovering over or about the selected " + "items. Otherwise it informs you about the currently viewed folder.<nl/>" + "For single items a preview of their contents is provided.</para>")); + infoDock->setWhatsThis(xi18nc("@info:whatsthis", "<para>This panel " + "provides in-depth information about the items your mouse is " + "hovering over or about the selected items. Otherwise it informs " + "you about the currently viewed folder.<nl/>For single items a " + "preview of their contents is provided.</para><para>You can configure " + "which and how details are given here by right-clicking.</para>") + panelWhatsThis); + // Setup "Folders" DolphinDockWidget* foldersDock = new DolphinDockWidget(i18nc("@title:window", "Folders")); foldersDock->setLocked(lock); @@ -1389,6 +1507,17 @@ void DolphinMainWindow::setupDockWidgets() connect(foldersPanel, &FoldersPanel::errorMessage, this, &DolphinMainWindow::showErrorMessage); + actionCollection()->action(QStringLiteral("show_folders_panel")) + ->setWhatsThis(xi18nc("@info:whatsthis", "This toggles the " + "<emphasis>folders</emphasis> panel at the left side of the window." + "<nl/><nl/>It shows the folders of the <emphasis>file system" + "</emphasis> in a <emphasis>tree view</emphasis>.")); + foldersDock->setWhatsThis(xi18nc("@info:whatsthis", "<para>This panel " + "shows the folders of the <emphasis>file system</emphasis> in a " + "<emphasis>tree view</emphasis>.</para><para>Click a folder to go " + "there. Click the arrow to the left of a folder to see its subfolders. " + "This allows quick switching between any folders.</para>") + panelWhatsThis); + // Setup "Terminal" #ifdef HAVE_TERMINAL if (KAuthorized::authorize(QStringLiteral("shell_access"))) { @@ -1416,6 +1545,22 @@ void DolphinMainWindow::setupDockWidgets() if (GeneralSettings::version() < 200) { terminalDock->hide(); } + + actionCollection()->action(QStringLiteral("show_terminal_panel")) + ->setWhatsThis(xi18nc("@info:whatsthis", "<para>This toggles the " + "<emphasis>terminal</emphasis> panel at the bottom of the window." + "<nl/>The location in the terminal will always match the folder " + "view so you can navigate using either.</para><para>The terminal " + "panel is not needed for basic computer usage but can be useful " + "for advanced tasks. To learn more about terminals use the help " + "in a standalone terminal application like Konsole.</para>")); + terminalDock->setWhatsThis(xi18nc("@info:whatsthis", "<para>This is " + "the <emphasis>terminal</emphasis> panel. It behaves like a " + "normal terminal but will match the location of the folder view " + "so you can navigate using either.</para><para>The terminal panel " + "is not needed for basic computer usage but can be useful for " + "advanced tasks. To learn more about terminals use the help in a " + "standalone terminal application like Konsole.</para>") + panelWhatsThis); } #endif @@ -1459,6 +1604,9 @@ void DolphinMainWindow::setupDockWidgets() auto actionShowAllPlaces = new QAction(QIcon::fromTheme(QStringLiteral("hint")), i18nc("@item:inmenu", "Show Hidden Places"), this); actionShowAllPlaces->setCheckable(true); actionShowAllPlaces->setDisabled(true); + actionShowAllPlaces->setWhatsThis(i18nc("@info:whatsthis", "This displays " + "all places in the places panel that have been hidden. They will " + "appear semi-transparent unless you uncheck their hide property.")); connect(actionShowAllPlaces, &QAction::triggered, this, [actionShowAllPlaces, this](bool checked){ actionShowAllPlaces->setIcon(QIcon::fromTheme(checked ? QStringLiteral("visibility") : QStringLiteral("hint"))); @@ -1470,6 +1618,25 @@ void DolphinMainWindow::setupDockWidgets() actionShowAllPlaces->setIcon(QIcon::fromTheme(checked ? QStringLiteral("visibility") : QStringLiteral("hint"))); }); + actionCollection()->action(QStringLiteral("show_places_panel")) + ->setWhatsThis(xi18nc("@info:whatsthis", "<para>This toggles the " + "<emphasis>places</emphasis> panel at the left side of the window." + "</para><para>It allows you to go to locations you have " + "bookmarked and to access disk or media attached to the computer " + "or to the network. It also contains sections to find recently " + "saved files or files of a certain type.</para>")); + placesDock->setWhatsThis(xi18nc("@info:whatsthis", "<para>This is the " + "<emphasis>Places</emphasis> panel. It allows you to go to locations " + "you have bookmarked and to access disk or media attached to the " + "computer or to the network. It also contains sections to find " + "recently saved files or files of a certain type.</para><para>" + "Click on an entry to go there. Click with the right mouse button " + "instead to open any entry in a new tab or new window.</para>" + "<para>New entries can be added by dragging folders onto this panel. " + "Right-click any section or entry to hide it. Right-click an empty " + "space on this panel and select <interface>Show Hidden Places" + "</interface> to display it again.</para>") + panelWhatsThis); + // Add actions into the "Panels" menu KActionMenu* panelsMenu = new KActionMenu(i18nc("@action:inmenu View", "Panels"), this); actionCollection()->addAction(QStringLiteral("panels"), panelsMenu); @@ -1536,6 +1703,16 @@ void DolphinMainWindow::updateGoActions() { QAction* goUpAction = actionCollection()->action(KStandardAction::name(KStandardAction::Up)); const QUrl currentUrl = m_activeViewContainer->url(); + // I think this is one of the best places to firstly be confronted + // with a file system and its hierarchy. Talking about the root + // directory might seem too much here but it is the question that + // naturally arises in this context. + goUpAction->setWhatsThis(xi18nc("@info:whatsthis", "<para>Go to " + "the folder that contains the currenty viewed one.</para>" + "<para>All files and folders are organized in a hierarchical " + "<emphasis>file system</emphasis>. At the top of this hierarchy is " + "a directory that contains all data connected to this computer" + "—the <emphasis>root directory</emphasis>.</para>")); goUpAction->setEnabled(KIO::upUrl(currentUrl) != currentUrl); } @@ -1549,11 +1726,13 @@ void DolphinMainWindow::createControlButton() m_controlButton = new QToolButton(this); m_controlButton->setIcon(QIcon::fromTheme(QStringLiteral("application-menu"))); m_controlButton->setText(i18nc("@action", "Control")); + m_controlButton->setAttribute(Qt::WidgetAttribute::WA_CustomWhatsThis); m_controlButton->setPopupMode(QToolButton::InstantPopup); m_controlButton->setToolButtonStyle(toolBar()->toolButtonStyle()); QMenu* controlMenu = new QMenu(m_controlButton); connect(controlMenu, &QMenu::aboutToShow, this, &DolphinMainWindow::updateControlMenu); + controlMenu->installEventFilter(this); m_controlButton->setMenu(controlMenu); @@ -1708,6 +1887,184 @@ void DolphinMainWindow::createPanelAction(const QIcon& icon, connect(dockAction, &QAction::toggled, panelAction, &QAction::setChecked); } +void DolphinMainWindow::setupWhatsThis() +{ + // main widgets + menuBar()->setWhatsThis(xi18nc("@info:whatsthis", "<para>This is the " + "<emphasis>Menubar</emphasis>. It provides access to commands and " + "configuration options. Left-click on any of the menus on this " + "bar to see its contents.</para><para>The Menubar can be hidden " + "by unchecking <interface>Settings|Show Menubar</interface>. Then " + "most of its contents become available through a <interface>Control" + "</interface> button on the <emphasis>Toolbar</emphasis>.</para>")); + toolBar()->setWhatsThis(xi18nc("@info:whatsthis", "<para>This is the " + "<emphasis>Toolbar</emphasis>. It allows quick access to " + "frequently used actions.</para><para>It is highly customizable. " + "All items you see in the <interface>Control</interface> menu or " + "in the <interface>Menubar</interface> can be placed on the " + "Toolbar. Just right-click on it and select <interface>Configure " + "Toolbars…</interface> or find this action in the <interface>" + "Control</interface> or <interface>Settings</interface> menu." + "</para><para>The location of the bar and the style of its " + "buttons can also be changed in the right-click menu. Right-click " + "a button if you want to show or hide its text.</para>")); + m_tabWidget->setWhatsThis(xi18nc("@info:whatsthis main view", + "<para>Here you can see the <emphasis>folders</emphasis> and " + "<emphasis>files</emphasis> that are at the location described in " + "the <interface>Location Bar</interface> above. This area is the " + "central part of this application where you navigate to the files " + "you want to use.</para><para>For an elaborate and general " + "introduction to this application <link " + "url='https://userbase.kde.org/Dolphin/File_Management#Introduction_to_Dolphin'>" + "click here</link>. This will open an introductory article from " + "the <emphasis>KDE UserBase Wiki</emphasis>.</para><para>For brief " + "explanations of all the features of this <emphasis>view</emphasis> " + "<link url='help:/dolphin/dolphin-view.html'>click here</link> " + "instead. This will open a page from the <emphasis>Handbook" + "</emphasis> that covers the basics.</para>")); + + // Settings menu + actionCollection()->action(KStandardAction::name(KStandardAction::KeyBindings)) + ->setWhatsThis(xi18nc("@info:whatsthis","<para>This opens a window " + "that lists the <emphasis>keyboard shortcuts</emphasis>.<nl/>" + "There you can set up key combinations to trigger an action when " + "they are pressed simultaneously. All commands in this application can " + "be triggered this way.</para>")); + actionCollection()->action(KStandardAction::name(KStandardAction::ConfigureToolbars)) + ->setWhatsThis(xi18nc("@info:whatsthis","<para>This opens a window in which " + "you can change which buttons appear on the <emphasis>Toolbar</emphasis>.</para>" + "<para>All items you see in the <interface>Control</interface> menu " + "or in the <interface>Menubar</interface> can also be placed on the Toolbar.</para>")); + actionCollection()->action(KStandardAction::name(KStandardAction::Preferences)) + ->setWhatsThis(xi18nc("@info:whatsthis","This opens a window where you can " + "change a multitude of settings for this application. For an explanation " + "of the various settings go to the chapter <emphasis>Configuring Dolphin" + "</emphasis> in <interface>Help|Dolphin Handbook</interface>.")); + + // Help menu + // The whatsthis has to be set for the m_helpMenu and for the + // StandardAction separately because both are used in different locations. + // m_helpMenu is only used for createControlButton() button. + + // Links do not work within the Menubar so texts without links are provided there. + + // i18n: If the external link isn't available in your language you should + // probably state the external link language at least in brackets to not + // frustrate the user. If there are multiple languages that the user might + // know with a reasonable chance you might want to have 2 external links. + // The same is in my opinion true for every external link you translate. + const QString whatsThisHelpContents = xi18nc("@info:whatsthis handbook", + "<para>This opens the Handbook for this application. It provides " + "explanations for every part of <emphasis>Dolphin</emphasis>.</para>"); + actionCollection()->action(KStandardAction::name(KStandardAction::HelpContents)) + ->setWhatsThis(whatsThisHelpContents + + xi18nc("@info:whatsthis second half of handbook hb text without link", + "<para>If you want more elaborate introductions to the " + "different features of <emphasis>Dolphin</emphasis> " + "go to the KDE UserBase Wiki.</para>")); + m_helpMenu->action(KHelpMenu::menuHelpContents)->setWhatsThis(whatsThisHelpContents + + xi18nc("@info:whatsthis second half of handbook text with link", + "<para>If you want more elaborate introductions to the " + "different features of <emphasis>Dolphin</emphasis> " + "<link url='https://userbase.kde.org/Dolphin/File_Management'>click here</link>. " + "It will open the dedicated page in the KDE UserBase Wiki.</para>")); + + const QString whatsThisWhatsThis = xi18nc("@info:whatsthis whatsthis button", + "<para>This is the button that invokes the help feature you are " + "using right now! Click it, then click any component of this " + "application to ask \"What's this?\" about it. The mouse cursor " + "will change appearance if no help is available for a spot.</para>"); + actionCollection()->action(KStandardAction::name(KStandardAction::WhatsThis)) + ->setWhatsThis(whatsThisWhatsThis + + xi18nc("@info:whatsthis second half of whatsthis button text without link", + "<para>There are two other ways to get help for this application: The " + "<interface>Dolphin Handbook</interface> in the <interface>Help" + "</interface> menu and the <emphasis>KDE UserBase Wiki</emphasis> " + "article about <emphasis>File Management</emphasis> online." + "</para><para>The \"What's this?\" help is " + "missing in most other windows so don't get too used to this.</para>")); + m_helpMenu->action(KHelpMenu::menuWhatsThis)->setWhatsThis(whatsThisWhatsThis + + xi18nc("@info:whatsthis second half of whatsthis button text with link", + "<para>There are two other ways to get help: " + "The <link url='help:/dolphin/index.html'>Dolphin Handbook</link> and " + "the <link url='https://userbase.kde.org/Dolphin/File_Management'>KDE " + "UserBase Wiki</link>.</para><para>The \"What's this?\" help is " + "missing in most other windows so don't get too used to this.</para>")); + + const QString whatsThisReportBug = xi18nc("@info:whatsthis","<para>This opens a " + "window that will guide you through reporting errors or flaws " + "in this application or in other KDE software.</para>"); + actionCollection()->action(KStandardAction::name(KStandardAction::ReportBug)) + ->setWhatsThis(whatsThisReportBug); + m_helpMenu->action(KHelpMenu::menuReportBug)->setWhatsThis(whatsThisReportBug + + xi18nc("@info:whatsthis second half of reportbug text with link", + "<para>High-quality bug reports are much appreciated. To learn " + "how to make your bug report as effective as possible " + "<link url='https://community.kde.org/Get_Involved/Bug_Reporting'>" + "click here</link>.</para>")); + + const QString whatsThisDonate = xi18nc("@info:whatsthis","<para>This opens a " + "<emphasis>web page</emphasis> where you can donate to " + "support the continued work on this application and many " + "other projects by the <emphasis>KDE</emphasis> community.</para>" + "<para>Donating is the easiest and fastest way to efficiently " + "support KDE and its projects. KDE projects are available for " + "free therefore your donation is needed to cover things that " + "require money like servers, contributor meetings, etc.</para>" + "<para><emphasis>KDE e.V.</emphasis> is the non-profit " + "organization behind the KDE community.</para>"); + actionCollection()->action(KStandardAction::name(KStandardAction::Donate)) + ->setWhatsThis(whatsThisDonate); + m_helpMenu->action(KHelpMenu::menuDonate)->setWhatsThis(whatsThisDonate); + + const QString whatsThisSwitchLanguage = xi18nc("@info:whatsthis", + "With this you can change the language this application uses." + "<nl/>You can even set secondary languages which will be used " + "if texts are not available in your preferred language."); + actionCollection()->action(KStandardAction::name(KStandardAction::SwitchApplicationLanguage)) + ->setWhatsThis(whatsThisSwitchLanguage); + m_helpMenu->action(KHelpMenu::menuSwitchLanguage)->setWhatsThis(whatsThisSwitchLanguage); + + const QString whatsThisAboutApp = xi18nc("@info:whatsthis","This opens a " + "window that informs you about the version, license, " + "used libraries and maintainers of this application."); + actionCollection()->action(KStandardAction::name(KStandardAction::AboutApp)) + ->setWhatsThis(whatsThisAboutApp); + m_helpMenu->action(KHelpMenu::menuAboutApp)->setWhatsThis(whatsThisAboutApp); + + const QString whatsThisAboutKDE = xi18nc("@info:whatsthis","This opens a " + "window with information about <emphasis>KDE</emphasis>. " + "The KDE community are the people behind this free software." + "<nl/>If you like using this application but don't know " + "about KDE or want to see a cute dragon have a look!"); + actionCollection()->action(KStandardAction::name(KStandardAction::AboutKDE)) + ->setWhatsThis(whatsThisAboutKDE); + m_helpMenu->action(KHelpMenu::menuAboutKDE)->setWhatsThis(whatsThisAboutKDE); +} + +bool DolphinMainWindow::event(QEvent *event) +{ + if (event->type() == QEvent::WhatsThisClicked) { + event->accept(); + QWhatsThisClickedEvent* whatsThisEvent = dynamic_cast<QWhatsThisClickedEvent*>(event); + QDesktopServices::openUrl(QUrl(whatsThisEvent->href())); + return true; + } + return KXmlGuiWindow::event(event); +} + +bool DolphinMainWindow::eventFilter(QObject* obj, QEvent* event) +{ + Q_UNUSED(obj) + if (event->type() == QEvent::WhatsThisClicked) { + event->accept(); + QWhatsThisClickedEvent* whatsThisEvent = dynamic_cast<QWhatsThisClickedEvent*>(event); + QDesktopServices::openUrl(QUrl(whatsThisEvent->href())); + return true; + } + return false; +} + DolphinMainWindow::UndoUiInterface::UndoUiInterface() : KIO::FileUndoManager::UiInterface() { diff --git a/src/dolphinmainwindow.h b/src/dolphinmainwindow.h index 4037c1468..dcfd9bce2 100644 --- a/src/dolphinmainwindow.h +++ b/src/dolphinmainwindow.h @@ -46,6 +46,7 @@ class KFileItem; class KFileItemList; class KJob; class KNewFileMenu; +class KHelpMenu; class QToolButton; class QIcon; class PlacesPanel; @@ -205,6 +206,11 @@ protected: /** @see KMainWindow::readProperties() */ void readProperties(const KConfigGroup& group) override; + /** Handles QWhatsThisClickedEvent and passes all others on. */ + bool event(QEvent* event) override; + /** Handles QWhatsThisClickedEvent and passes all others on. */ + bool eventFilter(QObject*, QEvent*) override; + private slots: /** * Refreshes the views of the main window by recreating them according to @@ -496,8 +502,16 @@ private slots: void slotToolBarActionMiddleClicked(QAction *action); private: + /** + * Sets up the various menus and actions and connects them. + */ void setupActions(); + + /** + * Sets up the dock widgets and their panels. + */ void setupDockWidgets(); + void updateEditActions(); void updateViewActions(); void updateGoActions(); @@ -541,6 +555,9 @@ private: QAction* dockAction, const QString& actionName); + /** Adds "What's This?" texts to many widgets and StandardActions. */ + void setupWhatsThis(); + private: /** * Implements a custom error handling for the undo manager. This @@ -556,6 +573,7 @@ private: }; KNewFileMenu* m_newFileMenu; + KHelpMenu* m_helpMenu; DolphinTabWidget* m_tabWidget; DolphinViewContainer* m_activeViewContainer; diff --git a/src/dolphinviewcontainer.cpp b/src/dolphinviewcontainer.cpp index 1e5d0f7d1..5d1d257e5 100644 --- a/src/dolphinviewcontainer.cpp +++ b/src/dolphinviewcontainer.cpp @@ -80,6 +80,18 @@ DolphinViewContainer::DolphinViewContainer(const QUrl& url, QWidget* parent) : QHBoxLayout* navigatorLayout = new QHBoxLayout(m_navigatorWidget); navigatorLayout->setSpacing(0); navigatorLayout->setContentsMargins(0, 0, 0, 0); + m_navigatorWidget->setWhatsThis(xi18nc("@info:whatsthis location bar", + "<para>This line describes the location of the files and folders " + "displayed below.</para><para>The name of the currently viewed " + "folder can be read at the very right. To the left of it is the " + "name of the folder that contains it. The whole line is called " + "the <emphasis>path</emphasis> to the current location because " + "following these folders from left to right leads here.</para>" + "<para>The path is displayed on the <emphasis>location bar</emphasis> " + "which is more powerful than one would expect. To learn more " + "about the basic and advanced features of the location bar " + "<link url='help:/dolphin/location-bar.html'>click here</link>. " + "This will open the dedicated page in the Handbook.</para>")); m_urlNavigator = new KUrlNavigator(DolphinPlacesModelSingleton::instance().placesModel(), url, this); connect(m_urlNavigator, &KUrlNavigator::activated, @@ -107,6 +119,18 @@ DolphinViewContainer::DolphinViewContainer(const QUrl& url, QWidget* parent) : connect(m_searchBox, &DolphinSearchBox::closeRequest, this, &DolphinViewContainer::closeSearchBox); connect(m_searchBox, &DolphinSearchBox::searchRequest, this, &DolphinViewContainer::startSearching); connect(m_searchBox, &DolphinSearchBox::returnPressed, this, &DolphinViewContainer::requestFocus); + m_searchBox->setWhatsThis(xi18nc("@info:whatsthis findbar", + "<para>This helps you find files and folders. Enter a <emphasis>" + "search term</emphasis> and specify search settings with the " + "buttons at the bottom:<list><item>Filename/Content: " + "Does the item you are looking for contain the search terms " + "within its filename or its contents?<nl/>The contents of images, " + "audio files and videos will not be searched.</item><item>" + "From Here/Everywhere: Do you want to search in this " + "folder and its sub-folders or everywhere?</item><item>" + "More Options: Click this to search by media type, access " + "time or rating.</item><item>More Search Tools: Install other " + "means to find an item.</item></list></para>")); m_messageWidget = new KMessageWidget(this); m_messageWidget->setCloseButtonVisible(true); diff --git a/src/statusbar/dolphinstatusbar.cpp b/src/statusbar/dolphinstatusbar.cpp index 0feaa119b..41c787eaa 100644 --- a/src/statusbar/dolphinstatusbar.cpp +++ b/src/statusbar/dolphinstatusbar.cpp @@ -131,6 +131,15 @@ DolphinStatusBar::DolphinStatusBar(QWidget* parent) : topLayout->addWidget(m_progressBar); setExtensionsVisible(true); + setWhatsThis(xi18nc("@info:whatsthis Statusbar", "<para>This is " + "the <emphasis>Statusbar</emphasis>. It contains three elements " + "by default (left to right):<list><item>A <emphasis>text field" + "</emphasis> that displays the size of selected items. If only " + "one item is selected the name and type is shown as well.</item>" + "<item>A <emphasis>zoom slider</emphasis> that allows you " + "to adjust the size of the icons in the view.</item>" + "<item><emphasis>Space information</emphasis> about the " + "current storage device.</item></list></para>")); } DolphinStatusBar::~DolphinStatusBar() diff --git a/src/views/dolphinviewactionhandler.cpp b/src/views/dolphinviewactionhandler.cpp index 6e5468cd5..6169ec2c1 100644 --- a/src/views/dolphinviewactionhandler.cpp +++ b/src/views/dolphinviewactionhandler.cpp @@ -99,7 +99,10 @@ void DolphinViewActionHandler::createActions() // File menu - KStandardAction::renameFile(this, &DolphinViewActionHandler::slotRename, m_actionCollection); + auto renameAction = KStandardAction::renameFile(this, &DolphinViewActionHandler::slotRename, m_actionCollection); + renameAction->setWhatsThis(xi18nc("@info:whatsthis", "This renames the " + "items in your current selection.<nl/>Renaming multiple items " + "at once amounts to their new names differing only in a number.")); auto trashAction = KStandardAction::moveToTrash(this, &DolphinViewActionHandler::slotTrashActivated, m_actionCollection); auto trashShortcuts = trashAction->shortcuts(); @@ -107,6 +110,10 @@ void DolphinViewActionHandler::createActions() trashShortcuts.append(QKeySequence::Delete); m_actionCollection->setDefaultShortcuts(trashAction, trashShortcuts); } + trashAction->setWhatsThis(xi18nc("@info:whatsthis", "This moves the " + "items in your current selection to the <filename>Trash" + "</filename>.<nl/>The trash is a temporary storage where " + "items can be deleted from if disk space is needed.")); auto deleteAction = KStandardAction::deleteFile(this, &DolphinViewActionHandler::slotDeleteItems, m_actionCollection); auto deleteShortcuts = deleteAction->shortcuts(); @@ -114,6 +121,9 @@ void DolphinViewActionHandler::createActions() deleteShortcuts.append(Qt::SHIFT | Qt::Key_Delete); m_actionCollection->setDefaultShortcuts(deleteAction, deleteShortcuts); } + deleteAction->setWhatsThis(xi18nc("@info:whatsthis", "This deletes " + "the items in your current selection completely. They can " + "not be recovered by normal means.")); // This action is useful for being enabled when KStandardAction::MoveToTrash should be // disabled and KStandardAction::DeleteFile is enabled (e.g. non-local files), so that Key_Del @@ -129,6 +139,12 @@ void DolphinViewActionHandler::createActions() QAction *propertiesAction = m_actionCollection->addAction( QStringLiteral("properties") ); // Well, it's the File menu in dolphinmainwindow and the Edit menu in dolphinpart... :) propertiesAction->setText( i18nc("@action:inmenu File", "Properties") ); + propertiesAction->setWhatsThis(xi18nc("@info:whatsthis properties", + "This shows a complete list of properties of the currently " + "selected items in a new window.<nl/>If nothing is selected the " + "window will be about the currently viewed folder instead.<nl/>" + "You can configure advanced options there like managing " + "read- and write-permissions.")); propertiesAction->setIcon(QIcon::fromTheme(QStringLiteral("document-properties"))); m_actionCollection->setDefaultShortcuts(propertiesAction, {Qt::ALT + Qt::Key_Return, Qt::ALT + Qt::Key_Enter}); connect(propertiesAction, &QAction::triggered, this, &DolphinViewActionHandler::slotProperties); @@ -138,6 +154,27 @@ void DolphinViewActionHandler::createActions() KToggleAction* compactAction = compactModeAction(); KToggleAction* detailsAction = detailsModeAction(); + iconsAction->setWhatsThis(xi18nc("@info:whatsthis Icons view mode", + "<para>This switches to a view mode that focuses on the folder " + "and file icons. This mode makes it easy to distinguish folders " + "from files and to detect items with distinctive <emphasis>" + "file types</emphasis>.</para><para> This mode is handy to " + "browse through pictures when the <interface>Preview" + "</interface> option is enabled.</para>")); + compactAction->setWhatsThis(xi18nc("@info:whatsthis Compact view mode", + "<para>This switches to a compact view mode that lists the folders " + "and files in columns with the names beside the icons. <para></para>" + "This helps to keep the overview in folders with many items.</para>")); + detailsAction->setWhatsThis(xi18nc("@info:whatsthis Details view mode", + "<para>This switches to a list view mode that focuses on folder " + "and file details.</para><para>Click on a detail in the column " + "header to sort the items by it. Click again to sort the other " + "way around. To select which details should be displayed click " + "the header with the right mouse button.</para><para>You can " + "view the contents of a folder without leaving the current " + "location by clicking to the left of it. This way you can view " + "the contents of multiple folders in the same list.</para>")); + KSelectAction* viewModeActions = m_actionCollection->add<KSelectAction>(QStringLiteral("view_mode")); viewModeActions->setText(i18nc("@action:intoolbar", "View Mode")); viewModeActions->addAction(iconsAction); @@ -146,17 +183,23 @@ void DolphinViewActionHandler::createActions() viewModeActions->setToolBarMode(KSelectAction::MenuMode); connect(viewModeActions, QOverload<QAction*>::of(&KSelectAction::triggered), this, &DolphinViewActionHandler::slotViewModeActionTriggered); - KStandardAction::zoomIn(this, + QAction* zoomInAction = KStandardAction::zoomIn(this, &DolphinViewActionHandler::zoomIn, m_actionCollection); + zoomInAction->setWhatsThis(i18nc("@info:whatsthis zoom in", "This increases the icon size.")); - KStandardAction::zoomOut(this, + QAction* zoomOutAction = KStandardAction::zoomOut(this, &DolphinViewActionHandler::zoomOut, m_actionCollection); + zoomOutAction->setWhatsThis(i18nc("@info:whatsthis zoom in", "This reduces the icon size.")); KToggleAction* showPreview = m_actionCollection->add<KToggleAction>(QStringLiteral("show_preview")); showPreview->setText(i18nc("@action:intoolbar", "Preview")); showPreview->setToolTip(i18nc("@info", "Show preview of files and folders")); + showPreview->setWhatsThis(xi18nc("@info:whatsthis", "When this is " + "enabled, the icons are based on the actual file or folder " + "contents.<nl/>For example the icons of images become scaled " + "down versions of the images.")); showPreview->setIcon(QIcon::fromTheme(QStringLiteral("view-preview"))); connect(showPreview, &KToggleAction::triggered, this, &DolphinViewActionHandler::togglePreview); @@ -197,16 +240,25 @@ void DolphinViewActionHandler::createActions() KToggleAction* showInGroups = m_actionCollection->add<KToggleAction>(QStringLiteral("show_in_groups")); showInGroups->setIcon(QIcon::fromTheme(QStringLiteral("view-group"))); showInGroups->setText(i18nc("@action:inmenu View", "Show in Groups")); + showInGroups->setWhatsThis(i18nc("@info:whatsthis", "This groups files and folders by their first letter.")); connect(showInGroups, &KToggleAction::triggered, this, &DolphinViewActionHandler::toggleGroupedSorting); KToggleAction* showHiddenFiles = m_actionCollection->add<KToggleAction>(QStringLiteral("show_hidden_files")); showHiddenFiles->setText(i18nc("@action:inmenu View", "Hidden Files")); showHiddenFiles->setToolTip(i18nc("@info", "Visibility of hidden files and folders")); + showHiddenFiles->setWhatsThis(xi18nc("@info:whatsthis", "<para>When " + "this is enabled <emphasis>hidden</emphasis> files and folders " + "are visible. They will be displayed semi-transparent.</para>" + "<para>Hidden items only differ from other ones in that their " + "name starts with a \".\". In general there is no need for " + "users to access them which is why they are hidden.</para>")); m_actionCollection->setDefaultShortcuts(showHiddenFiles, {Qt::ALT + Qt::Key_Period, Qt::CTRL + Qt::Key_H, Qt::Key_F8}); connect(showHiddenFiles, &KToggleAction::triggered, this, &DolphinViewActionHandler::toggleShowHiddenFiles); QAction* adjustViewProps = m_actionCollection->addAction(QStringLiteral("view_properties")); adjustViewProps->setText(i18nc("@action:inmenu View", "Adjust View Properties...")); + adjustViewProps->setWhatsThis(i18nc("@info:whatsthis", "This opens a window " + "in which all folder view properties can be adjusted.")); connect(adjustViewProps, &QAction::triggered, this, &DolphinViewActionHandler::slotAdjustViewProperties); } diff --git a/src/views/dolphinviewactionhandler.h b/src/views/dolphinviewactionhandler.h index 537adb4da..001a93d78 100644 --- a/src/views/dolphinviewactionhandler.h +++ b/src/views/dolphinviewactionhandler.h @@ -37,7 +37,7 @@ class KActionCollection; * @short Handles all actions for DolphinView * * The action handler owns all the actions and slots related to DolphinView, - * but can the view that is acts upon can be switched to another one + * but the view that it acts upon can be switched to another one * (this is used in the case of split views). * * The purpose of this class is also to share this code between DolphinMainWindow |
