2 * Copyright 2022-2024 Soren Stoutner <soren@stoutner.com>.
4 * This file is part of Privacy Browser PC <https://www.stoutner.com/privacy-browser-pc/>.
6 * Privacy Browser PC is free software: you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation, either version 3 of the License, or
9 * (at your option) any later version.
11 * Privacy Browser PC is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 * GNU General Public License for more details.
16 * You should have received a copy of the GNU General Public License
17 * along with Privacy Browser PC. If not, see <http://www.gnu.org/licenses/>.
20 // Application headers.
21 #include "BrowserWindow.h"
23 #include "databases/BookmarksDatabase.h"
24 #include "databases/DomainsDatabase.h"
25 #include "dialogs/AddBookmarkDialog.h"
26 #include "dialogs/AddFolderDialog.h"
27 #include "dialogs/BookmarksDialog.h"
28 #include "dialogs/CookiesDialog.h"
29 #include "dialogs/DomainSettingsDialog.h"
30 #include "dialogs/EditBookmarkDialog.h"
31 #include "dialogs/EditFolderDialog.h"
32 #include "dialogs/FilterListsDialog.h"
33 #include "dialogs/RequestsDialog.h"
34 #include "dialogs/SettingsDialog.h"
35 #include "helpers/SearchEngineHelper.h"
36 #include "helpers/UserAgentHelper.h"
37 #include "structs/BookmarkStruct.h"
39 // Qt toolkit headers.
41 #include <QContextMenuEvent>
42 #include <QDBusConnection>
43 #include <QDBusConnectionInterface>
44 #include <QDBusMessage>
45 #include <QGuiApplication>
46 #include <QInputDialog>
48 #include <QNetworkCookie>
50 #include <QMessageBox>
53 #include <QWebEngineFindTextResult>
55 // KDE Frameworks headers.
56 #include <KActionCollection>
57 #include <KColorScheme>
58 #include <KLocalizedString>
59 #include <KXMLGUIFactory>
61 // Construct the class.
62 BrowserWindow::BrowserWindow(bool firstWindow, QString *initialUrlStringPointer) : KXmlGuiWindow()
64 // Initialize the variables.
65 javaScriptEnabled = false;
66 localStorageEnabled = false;
68 // Instantiate the privacy tab widget pointer.
69 tabWidgetPointer = new TabWidget(this);
71 // Set the privacy tab widget as the central widget.
72 setCentralWidget(tabWidgetPointer);
74 // Get a handle for the action collection.
75 actionCollectionPointer = this->actionCollection();
77 // Add the standard actions.
78 KStandardAction::print(tabWidgetPointer, SLOT(print()), actionCollectionPointer);
79 QAction *printPreviewActionPointer = KStandardAction::printPreview(tabWidgetPointer, SLOT(printPreview()), actionCollectionPointer);
80 KStandardAction::quit(qApp, SLOT(closeAllWindows()), actionCollectionPointer);
81 zoomInActionPointer = KStandardAction::zoomIn(this, SLOT(incrementZoom()), actionCollectionPointer);
82 zoomOutActionPointer = KStandardAction::zoomOut(this, SLOT(decrementZoom()), actionCollectionPointer);
83 refreshActionPointer = KStandardAction::redisplay(this, SLOT(refresh()), actionCollectionPointer);
84 fullScreenActionPointer = KStandardAction::fullScreen(this, SLOT(toggleFullScreen()), this, actionCollectionPointer);
85 QAction *backActionPointer = KStandardAction::back(this, SLOT(back()), actionCollectionPointer);
86 QAction *forwardActionPointer = KStandardAction::forward(this, SLOT(forward()), actionCollectionPointer);
87 KStandardAction::home(this, SLOT(home()), actionCollectionPointer);
88 QAction *editBookmarksActionPointer = KStandardAction::editBookmarks(this, SLOT(editBookmarks()), actionCollectionPointer);
89 KStandardAction::preferences(this, SLOT(showSettingsDialog()), actionCollectionPointer);
90 KStandardAction::find(this, SLOT(showFindTextActions()), actionCollectionPointer);
91 findNextActionPointer = KStandardAction::findNext(this, SLOT(findNext()), actionCollectionPointer);
92 findPreviousActionPointer = KStandardAction::findPrev(this, SLOT(findPrevious()), actionCollectionPointer);
94 // Add the custom actions.
95 QAction *newTabActionPointer = actionCollectionPointer->addAction(QLatin1String("new_tab"));
96 QAction *newWindowActionPointer = actionCollectionPointer->addAction(QLatin1String("new_window"));
97 QAction *saveArchiveActionPointer = actionCollectionPointer->addAction(QLatin1String("save_archive"));
98 zoomDefaultActionPointer = actionCollectionPointer->addAction(QLatin1String("zoom_default"));
99 QAction *reloadAndBypassCacheActionPointer = actionCollectionPointer->addAction(QLatin1String("reload_and_bypass_cache"));
100 stopActionPointer = actionCollectionPointer->addAction(QLatin1String("stop"));
101 viewSourceActionPointer = actionCollectionPointer->addAction(QLatin1String("view_source"));
102 viewSourceInNewTabActionPointer = actionCollectionPointer->addAction(QLatin1String("view_source_in_new_tab"));
103 developerToolsActionPointer = actionCollectionPointer->addAction(QLatin1String("developer_tools"));
104 javaScriptActionPointer = actionCollectionPointer->addAction(QLatin1String("javascript"));
105 localStorageActionPointer = actionCollectionPointer->addAction(QLatin1String("local_storage"));
106 domStorageActionPointer = actionCollectionPointer->addAction(QLatin1String("dom_storage"));
107 userAgentPrivacyBrowserActionPointer = actionCollectionPointer->addAction(QLatin1String("user_agent_privacy_browser"));
108 userAgentWebEngineDefaultActionPointer = actionCollectionPointer->addAction(QLatin1String("user_agent_webengine_default"));
109 userAgentFirefoxLinuxActionPointer = actionCollectionPointer->addAction(QLatin1String("user_agent_firefox_linux"));
110 userAgentChromiumLinuxActionPointer = actionCollectionPointer->addAction(QLatin1String("user_agent_chromium_linux"));
111 userAgentFirefoxWindowsActionPointer = actionCollectionPointer->addAction(QLatin1String("user_agent_firefox_windows"));
112 userAgentChromeWindowsActionPointer = actionCollectionPointer->addAction(QLatin1String("user_agent_chrome_windows"));
113 userAgentEdgeWindowsActionPointer = actionCollectionPointer->addAction(QLatin1String("user_agent_edge_windows"));
114 userAgentSafariMacosActionPointer = actionCollectionPointer->addAction(QLatin1String("user_agent_safari_macos"));
115 userAgentCustomActionPointer = actionCollectionPointer->addAction(QLatin1String("user_agent_custom"));
116 zoomFactorActionPointer = actionCollectionPointer->addAction(QLatin1String("zoom_factor"));
117 searchEngineMojeekActionPointer = actionCollectionPointer->addAction(QLatin1String("search_engine_mojeek"));
118 searchEngineMonoclesActionPointer = actionCollectionPointer->addAction(QLatin1String("search_engine_monocles"));
119 searchEngineMetagerActionPointer = actionCollectionPointer->addAction(QLatin1String("search_engine_metager"));
120 searchEngineGoogleActionPointer = actionCollectionPointer->addAction(QLatin1String("search_engine_google"));
121 searchEngineBingActionPointer = actionCollectionPointer->addAction(QLatin1String("search_engine_bing"));
122 searchEngineYahooActionPointer = actionCollectionPointer->addAction(QLatin1String("search_engine_yahoo"));
123 searchEngineCustomActionPointer = actionCollectionPointer->addAction(QLatin1String("search_engine_custom"));
124 requestsActionPointer = actionCollectionPointer->addAction(QLatin1String("requests"));
125 QAction *viewFilterListsActionPointer = actionCollectionPointer->addAction(QLatin1String("view_filter_lists"));
126 viewBookmarksToolBarActionPointer = actionCollectionPointer->addAction(QLatin1String("view_bookmarks_toolbar"));
127 QAction *domainSettingsActionPointer = actionCollectionPointer->addAction(QLatin1String("domain_settings"));
128 cookiesActionPointer = actionCollectionPointer->addAction(QLatin1String("cookies"));
129 findCaseSensitiveActionPointer = actionCollectionPointer->addAction(QLatin1String("find_case_sensitive"));
130 hideFindTextActionPointer = actionCollectionPointer->addAction(QLatin1String("hide_find_actions"));
132 // Create the action groups
133 QActionGroup *userAgentActionGroupPointer = new QActionGroup(this);
134 QActionGroup *searchEngineActionGroupPointer = new QActionGroup(this);
136 // Add the actions to the groups.
137 userAgentActionGroupPointer->addAction(userAgentPrivacyBrowserActionPointer);
138 userAgentActionGroupPointer->addAction(userAgentWebEngineDefaultActionPointer);
139 userAgentActionGroupPointer->addAction(userAgentFirefoxLinuxActionPointer);
140 userAgentActionGroupPointer->addAction(userAgentChromiumLinuxActionPointer);
141 userAgentActionGroupPointer->addAction(userAgentFirefoxWindowsActionPointer);
142 userAgentActionGroupPointer->addAction(userAgentChromeWindowsActionPointer);
143 userAgentActionGroupPointer->addAction(userAgentEdgeWindowsActionPointer);
144 userAgentActionGroupPointer->addAction(userAgentSafariMacosActionPointer);
145 userAgentActionGroupPointer->addAction(userAgentCustomActionPointer);
146 searchEngineActionGroupPointer->addAction(searchEngineMojeekActionPointer);
147 searchEngineActionGroupPointer->addAction(searchEngineMonoclesActionPointer);
148 searchEngineActionGroupPointer->addAction(searchEngineMetagerActionPointer);
149 searchEngineActionGroupPointer->addAction(searchEngineGoogleActionPointer);
150 searchEngineActionGroupPointer->addAction(searchEngineBingActionPointer);
151 searchEngineActionGroupPointer->addAction(searchEngineYahooActionPointer);
152 searchEngineActionGroupPointer->addAction(searchEngineCustomActionPointer);
154 // Set some actions to be checkable.
155 javaScriptActionPointer->setCheckable(true);
156 localStorageActionPointer->setCheckable(true);
157 domStorageActionPointer->setCheckable(true);
158 findCaseSensitiveActionPointer->setCheckable(true);
159 viewSourceActionPointer->setCheckable(true);
160 developerToolsActionPointer->setCheckable(true);
161 userAgentPrivacyBrowserActionPointer->setCheckable(true);
162 userAgentWebEngineDefaultActionPointer->setCheckable(true);
163 userAgentFirefoxLinuxActionPointer->setCheckable(true);
164 userAgentChromiumLinuxActionPointer->setCheckable(true);
165 userAgentFirefoxWindowsActionPointer->setCheckable(true);
166 userAgentChromeWindowsActionPointer->setCheckable(true);
167 userAgentEdgeWindowsActionPointer->setCheckable(true);
168 userAgentSafariMacosActionPointer->setCheckable(true);
169 userAgentCustomActionPointer->setCheckable(true);
170 searchEngineMojeekActionPointer->setCheckable(true);
171 searchEngineMonoclesActionPointer->setCheckable(true);
172 searchEngineMetagerActionPointer->setCheckable(true);
173 searchEngineGoogleActionPointer->setCheckable(true);
174 searchEngineBingActionPointer->setCheckable(true);
175 searchEngineYahooActionPointer->setCheckable(true);
176 searchEngineCustomActionPointer->setCheckable(true);
177 viewBookmarksToolBarActionPointer->setCheckable(true);
179 // Instantiate the user agent helper.
180 UserAgentHelper *userAgentHelperPointer = new UserAgentHelper();
182 // Set the action text.
183 newTabActionPointer->setText(i18nc("New tab action", "New Tab"));
184 newWindowActionPointer->setText(i18nc("New window action", "New Window"));
185 saveArchiveActionPointer->setText(i18nc("Save archive action", "Save Archive"));
186 zoomDefaultActionPointer->setText(i18nc("Zoom default action", "Zoom Default"));
187 reloadAndBypassCacheActionPointer->setText(i18nc("Reload and bypass cache action", "Reload and Bypass Cache"));
188 stopActionPointer->setText(i18nc("Stop action", "Stop"));
189 viewSourceActionPointer->setText(i18nc("View source action", "View Source"));
190 viewSourceInNewTabActionPointer->setText(i18nc("View source in new tab action", "View Source in New Tab"));
191 developerToolsActionPointer->setText(i18nc("Developer tools action", "Developer Tools"));
192 javaScriptActionPointer->setText(i18nc("JavaScript action", "JavaScript"));
193 localStorageActionPointer->setText(i18nc("Local Storage action", "Local Storage"));
194 domStorageActionPointer->setText(i18nc("DOM Storage action", "DOM Storage"));
195 userAgentPrivacyBrowserActionPointer->setText(userAgentHelperPointer->PRIVACY_BROWSER_TRANSLATED);
196 userAgentWebEngineDefaultActionPointer->setText(userAgentHelperPointer->WEB_ENGINE_DEFAULT_TRANSLATED);
197 userAgentFirefoxLinuxActionPointer->setText(userAgentHelperPointer->FIREFOX_LINUX_TRANSLATED);
198 userAgentChromiumLinuxActionPointer->setText(userAgentHelperPointer->CHROMIUM_LINUX_TRANSLATED);
199 userAgentFirefoxWindowsActionPointer->setText(userAgentHelperPointer->FIREFOX_WINDOWS_TRANSLATED);
200 userAgentChromeWindowsActionPointer->setText(userAgentHelperPointer->CHROME_WINDOWS_TRANSLATED);
201 userAgentEdgeWindowsActionPointer->setText(userAgentHelperPointer->EDGE_WINDOWS_TRANSLATED);
202 userAgentSafariMacosActionPointer->setText(userAgentHelperPointer->SAFARI_MACOS_TRANSLATED);
203 searchEngineMojeekActionPointer->setText(i18nc("Search engine", "Mojeek"));
204 searchEngineMonoclesActionPointer->setText(i18nc("Search engine", "Monocles"));
205 searchEngineMetagerActionPointer->setText(i18nc("Search engine", "MetaGer"));
206 searchEngineGoogleActionPointer->setText(i18nc("Search engine", "Google"));
207 searchEngineBingActionPointer->setText(i18nc("Search engine", "Bing"));
208 searchEngineYahooActionPointer->setText(i18nc("Search engine", "Yahoo"));
209 requestsActionPointer->setText(i18nc("Requests action", "Requests - %1 Blocked", 0));
210 viewFilterListsActionPointer->setText(i18nc("View filter lists action", "View Filter Lists"));
211 viewBookmarksToolBarActionPointer->setText(i18nc("View bookmarks toolbar", "View Bookmarks Toolbar"));
212 domainSettingsActionPointer->setText(i18nc("Domain Settings action", "Domain Settings"));
213 cookiesActionPointer->setText(i18nc("The Cookies action, which also displays the number of cookies", "Cookies - %1", 0));
214 findCaseSensitiveActionPointer->setText(i18nc("Find Case Sensitive action", "Find Case Sensitive"));
215 hideFindTextActionPointer->setText(i18nc("Hide Find Text action (the text should include the language-specific escape keyboard shortcut).", "Hide Find Text (Esc)"));
217 // Set the action icons. Gnome doesn't contain some of the icons that KDE has.
218 // The toolbar icons don't pick up unless the size is explicit, probably because the toolbar ends up being an intermediate size.
219 newTabActionPointer->setIcon(QIcon::fromTheme(QLatin1String("tab-new")));
220 newWindowActionPointer->setIcon(QIcon::fromTheme(QLatin1String("window-new")));
221 saveArchiveActionPointer->setIcon(QIcon::fromTheme(QLatin1String("document-save")));
222 zoomDefaultActionPointer->setIcon(QIcon::fromTheme(QLatin1String("zoom-fit-best")));
223 reloadAndBypassCacheActionPointer->setIcon(QIcon::fromTheme(QLatin1String("view-refresh")));
224 stopActionPointer->setIcon(QIcon::fromTheme(QLatin1String("process-stop")));
225 viewSourceActionPointer->setIcon(QIcon::fromTheme(QLatin1String("view-choose"), QIcon::fromTheme(QLatin1String("accessories-text-editor"))));
226 viewSourceInNewTabActionPointer->setIcon(QIcon::fromTheme(QLatin1String("view-choose"), QIcon::fromTheme(QLatin1String("accessories-text-editor"))));
227 developerToolsActionPointer->setIcon(QIcon::fromTheme(QLatin1String("add-subtitle"), QIcon::fromTheme("system-run")));
228 domStorageActionPointer->setIcon(QIcon::fromTheme(QLatin1String("code-class"), QIcon(QLatin1String("/usr/share/icons/gnome/32x32/actions/gtk-unindent-ltr.png"))));
229 userAgentPrivacyBrowserActionPointer->setIcon(QIcon(QLatin1String(":/icons/privacy-mode.svg")));
230 userAgentWebEngineDefaultActionPointer->setIcon(QIcon::fromTheme(QLatin1String("qtlogo"), QIcon::fromTheme(QLatin1String("user-group-properties"),
231 QIcon::fromTheme(QLatin1String("contact-new")))));
232 userAgentFirefoxLinuxActionPointer->setIcon(QIcon::fromTheme(QLatin1String("firefox-esr"), QIcon::fromTheme(QLatin1String("user-group-properties"),
233 QIcon::fromTheme(QLatin1String("contact-new")))));
234 userAgentChromiumLinuxActionPointer->setIcon(QIcon::fromTheme(QLatin1String("chromium"), QIcon::fromTheme(QLatin1String("user-group-properties"), QIcon::fromTheme(QLatin1String("contact-new")))));
235 userAgentFirefoxWindowsActionPointer->setIcon(QIcon::fromTheme(QLatin1String("firefox-esr"), QIcon::fromTheme(QLatin1String("user-group-properties"),
236 QIcon::fromTheme(QLatin1String("contact-new")))));
237 userAgentChromeWindowsActionPointer->setIcon(QIcon::fromTheme(QLatin1String("chromium"), QIcon::fromTheme(QLatin1String("user-group-properties"), QIcon::fromTheme(QLatin1String("contact-new")))));
238 userAgentEdgeWindowsActionPointer->setIcon(QIcon::fromTheme(QLatin1String("user-group-properties"), QIcon::fromTheme(QLatin1String("contact-new"))));
239 userAgentSafariMacosActionPointer->setIcon(QIcon::fromTheme(QLatin1String("user-group-properties"), QIcon::fromTheme(QLatin1String("contact-new"))));
240 userAgentCustomActionPointer->setIcon(QIcon::fromTheme(QLatin1String("user-group-properties"), QIcon::fromTheme(QLatin1String("contact-new"))));
241 zoomFactorActionPointer->setIcon(QIcon::fromTheme(QLatin1String("zoom-fit-best")));
242 searchEngineMojeekActionPointer->setIcon(QIcon::fromTheme(QLatin1String("edit-find")));
243 searchEngineMonoclesActionPointer->setIcon(QIcon::fromTheme(QLatin1String("edit-find")));
244 searchEngineMetagerActionPointer->setIcon(QIcon::fromTheme(QLatin1String("edit-find")));
245 searchEngineGoogleActionPointer->setIcon(QIcon::fromTheme(QLatin1String("im-google"), QIcon::fromTheme(QLatin1String("edit-find"))));
246 searchEngineBingActionPointer->setIcon(QIcon::fromTheme(QLatin1String("edit-find")));
247 searchEngineYahooActionPointer->setIcon(QIcon::fromTheme(QLatin1String("im-yahoo"), QIcon::fromTheme(QLatin1String("edit-find"))));
248 searchEngineCustomActionPointer->setIcon(QIcon::fromTheme(QLatin1String("edit-find")));
249 requestsActionPointer->setIcon(QIcon::fromTheme(QLatin1String("document-equal"), QIcon::fromTheme(QLatin1String("system-lock-screen"))));
250 viewFilterListsActionPointer->setIcon(QIcon::fromTheme(QLatin1String("view-list-text"), QIcon::fromTheme(QLatin1String("format-justify-left"))));
251 editBookmarksActionPointer->setIcon(QIcon::fromTheme(QLatin1String("bookmark-edit"), QIcon::fromTheme(QLatin1String("bookmark-new"))));
252 viewBookmarksToolBarActionPointer->setIcon(QIcon::fromTheme(QLatin1String("bookmarks"), QIcon::fromTheme(QLatin1String("bookmark-new"))));
253 domainSettingsActionPointer->setIcon(QIcon::fromTheme(QLatin1String("settings-configure"), QIcon::fromTheme(QLatin1String("preferences-desktop"))));
254 cookiesActionPointer->setIcon(QIcon::fromTheme(QLatin1String("preferences-web-browser-cookies"), QIcon::fromTheme(QLatin1String("appointment-new"))));
255 findCaseSensitiveActionPointer->setIcon(QIcon::fromTheme(QLatin1String("format-text-lowercase"), QIcon::fromTheme(QLatin1String("/usr/share/icons/gnome/32x32/apps/fonts.png"))));
256 hideFindTextActionPointer->setIcon(QIcon::fromTheme(QLatin1String("window-close-symbolic")));
258 // Create the key sequences.
259 QKeySequence ctrlTKeySequence = QKeySequence(i18nc("The open new tab key sequence.", "Ctrl+T"));
260 QKeySequence ctrlNKeySequence = QKeySequence(i18nc("The open new window key sequence.", "Ctrl+N"));
261 QKeySequence ctrlAKeySequence = QKeySequence(i18nc("The save archive key sequence.", "Ctrl+A"));
262 QKeySequence ctrl0KeySequence = QKeySequence(i18nc("The zoom default key sequence.", "Ctrl+0"));
263 QKeySequence ctrlF5KeySequence = QKeySequence(i18nc("The reload and bypass cache key sequence.", "Ctrl+F5"));
264 QKeySequence ctrlShiftXKeySequence = QKeySequence(i18nc("The stop key sequence.", "Ctrl+Shift+X"));
265 QKeySequence ctrlUKeySequence = QKeySequence(i18nc("The view source key sequence.", "Ctrl+U"));
266 QKeySequence ctrlShiftUKeySequence = QKeySequence(i18nc("The view source in new tab key sequence.", "Ctrl+Shift+U"));
267 QKeySequence f12KeySequence = QKeySequence(i18nc("The developer tools key sequence.", "F12"));
268 QKeySequence ctrlShiftPKeySequence = QKeySequence(i18nc("The print preview key sequence.", "Ctrl+Shift+P"));
269 QKeySequence ctrlJKeySequence = QKeySequence(i18nc("The JavaScript key sequence.", "Ctrl+J"));
270 QKeySequence ctrlLKeySequence = QKeySequence(i18nc("The local storage key sequence.", "Ctrl+L"));
271 QKeySequence ctrlDKeySequence = QKeySequence(i18nc("The DOM storage key sequence.", "Ctrl+D"));
272 QKeySequence ctrlSKeySequence = QKeySequence(i18nc("The find case sensitive key sequence.", "Ctrl+S"));
273 QKeySequence ctrlAltPKeySequence = QKeySequence(i18nc("The Privacy Browser user agent key sequence.", "Ctrl+Alt+P"));
274 QKeySequence ctrlAltWKeySequence = QKeySequence(i18nc("The WebEngine Default user agent key sequence.", "Ctrl+Alt+W"));
275 QKeySequence ctrlAltFKeySequence = QKeySequence(i18nc("The Firefox on Linux user agent key sequence.", "Ctrl+Alt+F"));
276 QKeySequence ctrlAltCKeySequence = QKeySequence(i18nc("The Chromium on Linux user agent key sequence.", "Ctrl+Alt+C"));
277 QKeySequence ctrlAltShiftFKeySequence = QKeySequence(i18nc("The Firefox on Windows user agent key sequence.", "Ctrl+Alt+Shift+F"));
278 QKeySequence ctrlAltShiftCKeySequence = QKeySequence(i18nc("The Chrome on Windows user agent key sequence.", "Ctrl+Alt+Shift+C"));
279 QKeySequence ctrlAltEKeySequence = QKeySequence(i18nc("The Edge on Windows user agent key sequence.", "Ctrl+Alt+E"));
280 QKeySequence ctrlAltSKeySequence = QKeySequence(i18nc("The Safari on macOS user agent key sequence.", "Ctrl+Alt+S"));
281 QKeySequence altShiftCKeySequence = QKeySequence(i18nc("The custom user agent key sequence.", "Alt+Shift+C"));
282 QKeySequence ctrlAltZKeySequence = QKeySequence(i18nc("The zoom factor key sequence.", "Ctrl+Alt+Z"));
283 QKeySequence ctrlShiftMKeySequence = QKeySequence(i18nc("The Mojeek search engine key sequence.", "Ctrl+Shift+M"));
284 QKeySequence ctrlShiftOKeySequence = QKeySequence(i18nc("The Monocles search engine key sequence.", "Ctrl+Shift+O"));
285 QKeySequence ctrlShiftEKeySequence = QKeySequence(i18nc("The MetaGer search engine key sequence.", "Ctrl+Shift+E"));
286 QKeySequence ctrlShiftGKeySequence = QKeySequence(i18nc("The Google search engine key sequence.", "Ctrl+Shift+G"));
287 QKeySequence ctrlShiftBKeySequence = QKeySequence(i18nc("The Bing search engine key sequence.", "Ctrl+Shift+B"));
288 QKeySequence ctrlShiftYKeySequence = QKeySequence(i18nc("The Yahoo search engine key sequence.", "Ctrl+Shift+Y"));
289 QKeySequence ctrlShiftCKeySequence = QKeySequence(i18nc("The custom search engine key sequence.", "Ctrl+Shift+C"));
290 QKeySequence ctrlRKeySequence = QKeySequence(i18nc("The requests key sequence.", "Ctrl+R"));
291 QKeySequence ctrlShiftLKeySequence = QKeySequence(i18nc("The view filter lists key sequence.", "Ctrl+Shift+L"));
292 QKeySequence ctrlAltShiftBKeySequence = QKeySequence(i18nc("The edit bookmarks key sequence.", "Ctrl+Alt+Shift+B"));
293 QKeySequence ctrlAltBKeySequence = QKeySequence(i18nc("The view bookmarks toolbar key sequence.", "Ctrl+Alt+B"));
294 QKeySequence ctrlShiftDKeySequence = QKeySequence(i18nc("The domain settings key sequence.", "Ctrl+Shift+D"));
295 QKeySequence ctrlSemicolonKeySequence = QKeySequence(i18nc("The cookies dialog key sequence.", "Ctrl+;"));
297 // Set the action key sequences.
298 actionCollectionPointer->setDefaultShortcut(newTabActionPointer, ctrlTKeySequence);
299 actionCollectionPointer->setDefaultShortcut(newWindowActionPointer, ctrlNKeySequence);
300 actionCollectionPointer->setDefaultShortcut(saveArchiveActionPointer, ctrlAKeySequence);
301 actionCollectionPointer->setDefaultShortcut(zoomDefaultActionPointer, ctrl0KeySequence);
302 actionCollectionPointer->setDefaultShortcut(reloadAndBypassCacheActionPointer, ctrlF5KeySequence);
303 actionCollectionPointer->setDefaultShortcut(stopActionPointer, ctrlShiftXKeySequence);
304 actionCollectionPointer->setDefaultShortcut(viewSourceActionPointer, ctrlUKeySequence);
305 actionCollectionPointer->setDefaultShortcut(viewSourceInNewTabActionPointer, ctrlShiftUKeySequence);
306 actionCollectionPointer->setDefaultShortcut(developerToolsActionPointer, f12KeySequence);
307 actionCollectionPointer->setDefaultShortcut(printPreviewActionPointer, ctrlShiftPKeySequence);
308 actionCollectionPointer->setDefaultShortcut(javaScriptActionPointer, ctrlJKeySequence);
309 actionCollectionPointer->setDefaultShortcut(localStorageActionPointer, ctrlLKeySequence);
310 actionCollectionPointer->setDefaultShortcut(domStorageActionPointer, ctrlDKeySequence);
311 actionCollectionPointer->setDefaultShortcut(findCaseSensitiveActionPointer, ctrlSKeySequence);
312 actionCollectionPointer->setDefaultShortcut(userAgentPrivacyBrowserActionPointer, ctrlAltPKeySequence);
313 actionCollectionPointer->setDefaultShortcut(userAgentWebEngineDefaultActionPointer, ctrlAltWKeySequence);
314 actionCollectionPointer->setDefaultShortcut(userAgentFirefoxLinuxActionPointer, ctrlAltFKeySequence);
315 actionCollectionPointer->setDefaultShortcut(userAgentChromiumLinuxActionPointer, ctrlAltCKeySequence);
316 actionCollectionPointer->setDefaultShortcut(userAgentFirefoxWindowsActionPointer, ctrlAltShiftFKeySequence);
317 actionCollectionPointer->setDefaultShortcut(userAgentChromeWindowsActionPointer, ctrlAltShiftCKeySequence);
318 actionCollectionPointer->setDefaultShortcut(userAgentEdgeWindowsActionPointer, ctrlAltEKeySequence);
319 actionCollectionPointer->setDefaultShortcut(userAgentSafariMacosActionPointer, ctrlAltSKeySequence);
320 actionCollectionPointer->setDefaultShortcut(userAgentCustomActionPointer, altShiftCKeySequence);
321 actionCollectionPointer->setDefaultShortcut(zoomFactorActionPointer, ctrlAltZKeySequence);
322 actionCollectionPointer->setDefaultShortcut(searchEngineMojeekActionPointer, ctrlShiftMKeySequence);
323 actionCollectionPointer->setDefaultShortcut(searchEngineMonoclesActionPointer, ctrlShiftOKeySequence);
324 actionCollectionPointer->setDefaultShortcut(searchEngineMetagerActionPointer, ctrlShiftEKeySequence);
325 actionCollectionPointer->setDefaultShortcut(searchEngineGoogleActionPointer, ctrlShiftGKeySequence);
326 actionCollectionPointer->setDefaultShortcut(searchEngineBingActionPointer, ctrlShiftBKeySequence);
327 actionCollectionPointer->setDefaultShortcut(searchEngineYahooActionPointer, ctrlShiftYKeySequence);
328 actionCollectionPointer->setDefaultShortcut(searchEngineCustomActionPointer, ctrlShiftCKeySequence);
329 actionCollectionPointer->setDefaultShortcut(requestsActionPointer, ctrlRKeySequence);
330 actionCollectionPointer->setDefaultShortcut(viewFilterListsActionPointer, ctrlShiftLKeySequence);
331 actionCollectionPointer->setDefaultShortcut(editBookmarksActionPointer, ctrlAltShiftBKeySequence);
332 actionCollectionPointer->setDefaultShortcut(viewBookmarksToolBarActionPointer, ctrlAltBKeySequence);
333 actionCollectionPointer->setDefaultShortcut(domainSettingsActionPointer, ctrlShiftDKeySequence);
334 actionCollectionPointer->setDefaultShortcut(cookiesActionPointer, ctrlSemicolonKeySequence);
336 // Execute the actions.
337 connect(newTabActionPointer, SIGNAL(triggered()), tabWidgetPointer, SLOT(addTab()));
338 connect(newWindowActionPointer, SIGNAL(triggered()), this, SLOT(newWindow()));
339 connect(saveArchiveActionPointer, SIGNAL(triggered()), tabWidgetPointer, SLOT(saveArchive()));
340 connect(zoomDefaultActionPointer, SIGNAL(triggered()), this, SLOT(zoomDefault()));
341 connect(reloadAndBypassCacheActionPointer, SIGNAL(triggered()), this, SLOT(reloadAndBypassCache()));
342 connect(stopActionPointer, SIGNAL(triggered()), tabWidgetPointer, SLOT(stop()));
343 connect(viewSourceActionPointer, SIGNAL(triggered()), this, SLOT(toggleViewSource()));
344 connect(viewSourceInNewTabActionPointer, SIGNAL(triggered()), this, SLOT(toggleViewSourceInNewTab()));
345 connect(developerToolsActionPointer, SIGNAL(triggered()), this, SLOT(toggleDeveloperTools()));
346 connect(zoomFactorActionPointer, SIGNAL(triggered()), this, SLOT(getZoomFactorFromUser()));
347 connect(requestsActionPointer, SIGNAL(triggered()), this, SLOT(showRequestsDialog()));
348 connect(viewFilterListsActionPointer, SIGNAL(triggered()), this, SLOT(showFilterListsDialog()));
349 connect(viewBookmarksToolBarActionPointer, SIGNAL(triggered()), this, SLOT(toggleViewBookmarksToolBar()));
350 connect(cookiesActionPointer, SIGNAL(triggered()), this, SLOT(showCookiesDialog()));
351 connect(domainSettingsActionPointer, SIGNAL(triggered()), this, SLOT(showDomainSettingsDialog()));
353 // Update the on-the-fly menus.
354 connect(tabWidgetPointer, SIGNAL(updateUserAgentActions(QString, bool)), this, SLOT(updateUserAgentActions(QString, bool)));
355 connect(tabWidgetPointer, SIGNAL(updateZoomActions(double)), this, SLOT(updateZoomActions(double)));
356 connect(tabWidgetPointer, SIGNAL(updateSearchEngineActions(QString, bool)), this, SLOT(updateSearchEngineActions(QString, bool)));
358 // Apply the on-the-fly settings when selected.
359 connect(userAgentActionGroupPointer, SIGNAL(triggered(QAction*)), tabWidgetPointer, SLOT(applyOnTheFlyUserAgent(QAction*)));
360 connect(searchEngineActionGroupPointer, SIGNAL(triggered(QAction*)), tabWidgetPointer, SLOT(applyOnTheFlySearchEngine(QAction*)));
362 // Process blocked requests.
363 connect(tabWidgetPointer, SIGNAL(blockedRequestsUpdated(const int)), this, SLOT(updateRequestsAction(const int)));
365 // Process cookie changes.
366 connect(tabWidgetPointer, SIGNAL(cookiesChanged(const int)), this, SLOT(updateCookiesAction(const int)));
368 // Store the default zoom factor.
369 connect(tabWidgetPointer, SIGNAL(updateDefaultZoomFactor(double)), this, SLOT(updateDefaultZoomFactor(double)));
371 // Connect the URL toolbar actions.
372 connect(javaScriptActionPointer, SIGNAL(triggered()), this, SLOT(toggleJavaScript()));
373 connect(localStorageActionPointer, SIGNAL(triggered()), this, SLOT(toggleLocalStorage()));
374 connect(domStorageActionPointer, SIGNAL(triggered()), this, SLOT(toggleDomStorage()));
376 // Update the actions from the tab widget.
377 connect(tabWidgetPointer, SIGNAL(updateDeveloperToolsAction(bool)), developerToolsActionPointer, SLOT(setChecked(bool)));
378 connect(tabWidgetPointer, SIGNAL(updateBackAction(bool)), backActionPointer, SLOT(setEnabled(bool)));
379 connect(tabWidgetPointer, SIGNAL(updateForwardAction(bool)), forwardActionPointer, SLOT(setEnabled(bool)));
380 connect(tabWidgetPointer, SIGNAL(updateJavaScriptAction(bool)), this, SLOT(updateJavaScriptAction(bool)));
381 connect(tabWidgetPointer, SIGNAL(updateLocalStorageAction(bool)), this, SLOT(updateLocalStorageAction(bool)));
382 connect(tabWidgetPointer, SIGNAL(updateDomStorageAction(bool)), this, SLOT(updateDomStorageAction(bool)));
384 // Connect the find text actions.
385 connect(findCaseSensitiveActionPointer, SIGNAL(triggered()), this, SLOT(toggleFindCaseSensitive()));
386 connect(hideFindTextActionPointer, SIGNAL(triggered()), this, SLOT(hideFindTextActions()));
390 // Setup the GUI based on the browserwindowui.rc file.
391 setupGUI(StandardWindowOption::Default, ("browserwindowui.rc"));
393 // Get lists of the actions' associated widgets.
394 QList<QWidget*> userAgentAssociatedWidgetsPointerList = userAgentPrivacyBrowserActionPointer->associatedWidgets();
395 QList<QWidget*> searchEngineAssociatedWidgetsPointerList = searchEngineMojeekActionPointer->associatedWidgets();
397 // Get the menu widget pointers. It is the second entry, after the main window.
398 QWidget *userAgentMenuWidgetPointer = userAgentAssociatedWidgetsPointerList[1];
399 QWidget *searchEngineMenuWidgetPointer = searchEngineAssociatedWidgetsPointerList[1];
401 // Get the menu pointers.
402 QMenu *userAgentMenuPointer = qobject_cast<QMenu*>(userAgentMenuWidgetPointer);
403 QMenu *searchEngineMenuPointer = qobject_cast<QMenu*>(searchEngineMenuWidgetPointer);
405 // Get the menu actions.
406 userAgentMenuActionPointer = userAgentMenuPointer->menuAction();
407 searchEngineMenuActionPointer = searchEngineMenuPointer->menuAction();
409 // Get handles for the toolbars.
410 navigationToolBarPointer = toolBar(QLatin1String("navigation_toolbar"));
411 urlToolBarPointer = toolBar(QLatin1String("url_toolbar"));
412 bookmarksToolBarPointer = toolBar(QLatin1String("bookmarks_toolbar"));
414 // Populate the view bookmarks toolbar checkbox.
415 connect(bookmarksToolBarPointer, SIGNAL(visibilityChanged(bool)), this, SLOT(updateViewBookmarksToolBarCheckbox(bool)));
417 // Create the line edits.
418 urlLineEditPointer = new UrlLineEdit();
419 findTextLineEditPointer = new KLineEdit();
421 // Get the line edit size policies.
422 QSizePolicy urlLineEditSizePolicy = urlLineEditPointer->sizePolicy();
423 QSizePolicy findTextLineEditSizePolicy = findTextLineEditPointer->sizePolicy();
425 // Set the URL line edit horizontal stretch to be five times the find text line edit stretch.
426 urlLineEditSizePolicy.setHorizontalStretch(5);
427 findTextLineEditSizePolicy.setHorizontalStretch(1);
430 urlLineEditPointer->setSizePolicy(urlLineEditSizePolicy);
431 findTextLineEditPointer->setSizePolicy(findTextLineEditSizePolicy);
434 urlLineEditPointer->setMinimumWidth(350);
435 findTextLineEditPointer->setMinimumWidth(200);
436 findTextLineEditPointer->setMaximumWidth(350);
438 // Set the place holder text.
439 urlLineEditPointer->setPlaceholderText(i18nc("The URL line edit placeholder text", "URL or Search Terms"));
440 findTextLineEditPointer->setPlaceholderText(i18nc("The find line edit placeholder text", "Find Text"));
442 // Show the clear button on the find line edit.
443 findTextLineEditPointer->setClearButtonEnabled(true);
445 // Add the actions to the URL line edit.
446 bookmarkedActionPointer = urlLineEditPointer->addAction(QIcon::fromTheme("non-starred-symbolic"), QLineEdit::LeadingPosition);
447 QAction *addOrEditDomainSettingsActionPointer = urlLineEditPointer->addAction(QIcon::fromTheme("settings-configure", QIcon::fromTheme(QLatin1String("preferences-desktop"))),
448 QLineEdit::TrailingPosition);
450 // Set the bookmarked action pointer to be checkable.
451 bookmarkedActionPointer->setCheckable(true);
453 // Connect the URL line edit actions.
454 connect(bookmarkedActionPointer, SIGNAL(triggered()), this, SLOT(toggleBookmark()));
455 connect(addOrEditDomainSettingsActionPointer, SIGNAL(triggered()), this, SLOT(addOrEditDomainSettings()));
457 // Create a find text label pointer.
458 findTextLabelPointer = new QLabel();
460 // Set the default label text.
461 findTextLabelPointer->setText(QLatin1String(" ") + i18nc("Default find results.", "0/0") + QLatin1String(" "));
463 // Insert the widgets into the toolbars.
464 urlToolBarPointer->insertWidget(javaScriptActionPointer, urlLineEditPointer);
465 findTextLineEditActionPointer = urlToolBarPointer->insertWidget(findNextActionPointer, findTextLineEditPointer);
466 findTextLabelActionPointer = urlToolBarPointer->insertWidget(findNextActionPointer, findTextLabelPointer);
468 // Initially hide the find text actions.
469 hideFindTextActions();
471 // Load a new URL from the URL line edit.
472 connect(urlLineEditPointer, SIGNAL(returnKeyPressed(const QString)), this, SLOT(loadUrlFromLineEdit(const QString)));
474 // Find text as it is typed.
475 connect(findTextLineEditPointer, SIGNAL(textEdited(const QString &)), tabWidgetPointer, SLOT(findText(const QString &)));
477 // Find next if the enter key is pressed.
478 connect(findTextLineEditPointer, SIGNAL(returnKeyPressed(const QString &)), tabWidgetPointer, SLOT(findText(const QString &)));
480 // Update find text when switching tabs.
481 connect(tabWidgetPointer, SIGNAL(updateFindText(const QString &, const bool)), this, SLOT(updateFindText(const QString &, const bool)));
483 // Update the find text results.
484 connect(tabWidgetPointer, SIGNAL(updateFindTextResults(const QWebEngineFindTextResult &)), this, SLOT(updateFindTextResults(const QWebEngineFindTextResult &)));
486 // Update the URL line edit on page loads.
487 connect(tabWidgetPointer, SIGNAL(updateUrlLineEdit(QUrl)), this, SLOT(updateUrlLineEdit(QUrl)));
489 // Update the window title.
490 connect(tabWidgetPointer, SIGNAL(updateWindowTitle(const QString)), this, SLOT(updateWindowTitle(const QString)));
492 // Get a handle for the status bar.
493 QStatusBar *statusBarPointer = statusBar();
495 // Create the status bar widgets.
496 progressBarPointer = new QProgressBar();
497 zoomMinusButtonPointer = new QPushButton();
498 currentZoomButtonPointer = new QPushButton();
499 zoomPlusButtonPointer = new QPushButton();
501 // Set the button icons.
502 zoomMinusButtonPointer->setIcon(QIcon::fromTheme(QStringLiteral("list-remove-symbolic")));
503 zoomPlusButtonPointer->setIcon(QIcon::fromTheme(QStringLiteral("list-add-symbolic")));
505 // Set the button icons to be flat (no borders).
506 zoomMinusButtonPointer->setFlat(true);
507 currentZoomButtonPointer->setFlat(true);
508 zoomPlusButtonPointer->setFlat(true);
510 // Handle clicks on the zoom buttons.
511 connect(zoomMinusButtonPointer, SIGNAL(clicked()), this, SLOT(decrementZoom()));
512 connect(currentZoomButtonPointer, SIGNAL(clicked()), this, SLOT(getZoomFactorFromUser()));
513 connect(zoomPlusButtonPointer, SIGNAL(clicked()), this, SLOT(incrementZoom()));
515 // Remove the padding around the current zoom button text.
516 currentZoomButtonPointer->setStyleSheet("padding: 0px;");
518 // Add the widgets to the far right of the status bar.
519 statusBarPointer->addPermanentWidget(progressBarPointer);
520 statusBarPointer->addPermanentWidget(zoomMinusButtonPointer);
521 statusBarPointer->addPermanentWidget(currentZoomButtonPointer);
522 statusBarPointer->addPermanentWidget(zoomPlusButtonPointer);
524 // Update the status bar with the URL when a link is hovered.
525 connect(tabWidgetPointer, SIGNAL(linkHovered(QString)), statusBarPointer, SLOT(showMessage(QString)));
527 // Update the progress bar.
528 connect(tabWidgetPointer, SIGNAL(showProgressBar(const int)), this, SLOT(showProgressBar(const int)));
529 connect(tabWidgetPointer, SIGNAL(hideProgressBar()), this, SLOT(hideProgressBar()));
531 // Update the URL line edit focus.
532 connect(tabWidgetPointer, SIGNAL(clearUrlLineEditFocus()), this, SLOT(clearUrlLineEditFocus()));
534 // Get the URL line edit palettes.
535 normalBackgroundPalette = urlLineEditPointer->palette();
536 negativeBackgroundPalette = normalBackgroundPalette;
537 positiveBackgroundPalette = normalBackgroundPalette;
539 // Modify the palettes.
540 KColorScheme::adjustBackground(negativeBackgroundPalette, KColorScheme::NegativeBackground);
541 KColorScheme::adjustBackground(positiveBackgroundPalette, KColorScheme::PositiveBackground);
543 // Update the applied palette.
544 connect(tabWidgetPointer, SIGNAL(updateDomainSettingsIndicator(const bool)), this, SLOT(updateDomainSettingsIndicator(const bool)));
546 // Process full screen requests.
547 connect(tabWidgetPointer, SIGNAL(fullScreenRequested(bool)), this, SLOT(fullScreenRequested(bool)));
549 // Create keyboard shortcuts.
550 QShortcut *f11ShortcutPointer = new QShortcut(QKeySequence(i18nc("The toggle full screen shortcut.", "F11")), this);
551 QShortcut *escapeShortcutPointer = new QShortcut(QKeySequence::Cancel, this);
553 // Connect the keyboard shortcuts.
554 connect(f11ShortcutPointer, SIGNAL(activated()), fullScreenActionPointer, SLOT(trigger()));
555 connect(escapeShortcutPointer, SIGNAL(activated()), this, SLOT(escape()));
557 // Get a handle for the Bookmarks menu.
558 bookmarksMenuPointer = qobject_cast<QMenu*>(guiFactory()->container("bookmarks", this));
560 // Add a separator to the bookmarks menu.
561 bookmarksMenuPointer->addSeparator();
563 // Initialize the bookmark action lists.
564 bookmarkFolderFinalActionList = QList<QPair<QMenu *, QAction *> *>();
565 bookmarksMenuActionList = QList<QPair<QMenu *, QAction *> *>();
566 bookmarksMenuSubmenuList = QList<QPair<QMenu *, QMenu *> *>();
567 bookmarksToolBarActionList = QList<QAction*>();
568 bookmarksToolBarSubfolderActionList = QList<QPair<QMenu *, QAction *> *>();
570 // Set the bookmarks toolbar context menu policy.
571 bookmarksToolBarPointer->setContextMenuPolicy(Qt::CustomContextMenu);
573 // Show the custom bookmark context menu when requested.
574 connect(bookmarksToolBarPointer, SIGNAL(customContextMenuRequested(const QPoint&)), this, SLOT(showBookmarkContextMenu(const QPoint&)));
576 // Populate the bookmarks in this window.
577 populateBookmarksInThisWindow();
580 // This must be done here, because otherwise, if a URL is loaded, like a local file, that does not trigger a call to TabWidget::applyDomainSettings, the UI will not be fully populated.
581 updateJavaScriptAction(Settings::javaScriptEnabled());
582 updateLocalStorageAction(Settings::localStorageEnabled());
583 updateDomStorageAction(Settings::domStorageEnabled());
584 updateUserAgentActions(UserAgentHelper::getUserAgentFromDatabaseName(Settings::userAgent()), true);
585 updateZoomActions(Settings::zoomFactor());
587 // Populate the first tab.
588 if (firstWindow) // This is the first window.
590 // Load the initial website.
591 tabWidgetPointer->loadInitialWebsite();
593 else if (initialUrlStringPointer) // An initial URL was specified.
595 // Load the initial URL.
596 tabWidgetPointer->loadUrlFromLineEdit(*initialUrlStringPointer);
600 // If actions are part of a context menu they do not need to be added to the list as they will be deleted automatically when the context menu closes.
601 void BrowserWindow::addBookmarkFolderFinalActions(QMenu *menuPointer, const double folderId, const bool addToList)
603 // Get the database ID.
604 int folderDatabaseId = BookmarksDatabase::getFolderDatabaseId(folderId);
607 menuPointer->addSeparator();
609 // Add the add bookmark action to the menu.
610 QAction *addBookmarkActionPointer = menuPointer->addAction(QIcon::fromTheme(QLatin1String("bookmark-new")), i18nc("The add bookmark action", "Add Bookmark"), [=]
612 // Instantiate an add bookmark dialog.
613 AddBookmarkDialog *addBookmarkDialogPointer = new AddBookmarkDialog(this, tabWidgetPointer->getCurrentTabTitle(), tabWidgetPointer->getCurrentTabUrl(),
614 tabWidgetPointer->getCurrentTabFavoritIcon(), folderId);
616 // Update the displayed bookmarks when a new one is added.
617 connect(addBookmarkDialogPointer, SIGNAL(bookmarkAdded()), this, SLOT(populateBookmarksInAllWindows()));
620 addBookmarkDialogPointer->show();
624 // Add the add folder action to the menu.
625 QAction *addFolderActionPointer = menuPointer->addAction(QIcon::fromTheme(QLatin1String("folder-add")), i18nc("The add folder action", "Add Folder"), [=]
627 // Instantiate an add folder dialog.
628 AddFolderDialog *addFolderDialogPointer = new AddFolderDialog(this, tabWidgetPointer->getCurrentTabFavoritIcon(), folderId);
630 // Update the displayed bookmarks when a folder is added.
631 connect(addFolderDialogPointer, SIGNAL(folderAdded()), this, SLOT(populateBookmarksInAllWindows()));
634 addFolderDialogPointer->show();
639 menuPointer->addSeparator();
641 // Add the open folder in new tabs action to the menu.
642 QAction *openFolderInNewTabsActionPointer = menuPointer->addAction(QIcon::fromTheme(QLatin1String("tab-new")), i18nc("The open folder in new tabs action", "Open Folder in New Tabs"), [=]
644 // Get all the folder URLs.
645 QList<QString> *folderUrlsListPointer = BookmarksDatabase::getAllFolderUrls(folderId);
647 // Open the URLs in new tabs. `true` removes the URL line edit focus, `true` opens the new tabs in an adjacent tab. `false` does not load a background tab.
648 for (QString url : *folderUrlsListPointer)
649 tabWidgetPointer->addTab(true, true, false, url);
653 // Add the open folder in background tabs action to the menu.
654 QAction *openFolderInBackgroundTabsActionPointer = menuPointer->addAction(QIcon::fromTheme(QLatin1String("tab-new")),
655 i18nc("The open folder in background tabs action", "Open Folder in Background Tabs"), [=]
657 // Get all the folder URLs.
658 QList<QString> *folderUrlsListPointer = BookmarksDatabase::getAllFolderUrls(folderId);
660 // Open the URLs in new tabs. `true` removes the URL line edit focus, `true` opens the new tabs in an adjacent tab. `true` loads a background tab.
661 for (QString url : *folderUrlsListPointer)
662 tabWidgetPointer->addTab(true, true, true, url);
666 // Add the open folder in new window action to the menu.
667 QAction *openFolderInNewWindowActionPointer = menuPointer->addAction(QIcon::fromTheme(QLatin1String("window-new")), i18nc("The open folder in new window action", "Open Folder in New Window"), [=]
669 // Get all the folder URLs.
670 QList<QString> *folderUrlsListPointer = BookmarksDatabase::getAllFolderUrls(folderId);
672 // Create a new browser window.
673 BrowserWindow *browserWindowPointer = new BrowserWindow(false, &folderUrlsListPointer->first());
675 // Get a count of the folder URLs.
676 const int folderUrls = folderUrlsListPointer->count();
678 // Load all the other URLs. `true` removes the URL line edit focus, `false` does not load the new tabs in adjacent tabs. `true` loads a background tab.
679 for (int i = 1; i < folderUrls; ++i)
680 browserWindowPointer->tabWidgetPointer->addTab(true, false, true, folderUrlsListPointer->value(i));
682 // Show the new browser window.
683 browserWindowPointer->show();
688 menuPointer->addSeparator();
690 // Add the edit folder action to the menu if this is not the root bookmark menu.
693 QAction *editFolderActionPointer = menuPointer->addAction(QIcon::fromTheme(QLatin1String("document-edit")), i18nc("The edit folder action", "Edit Folder"), [=]
695 // Get the current tab favorite icon.
696 QIcon currentTabFavoriteIcon = tabWidgetPointer->getCurrentTabFavoritIcon();
698 // Instantiate an edit folder dialog.
699 QDialog *editFolderDialogPointer = new EditFolderDialog(this, folderDatabaseId, currentTabFavoriteIcon);
702 editFolderDialogPointer->show();
704 // Process bookmark events.
705 connect(editFolderDialogPointer, SIGNAL(folderSaved()), this, SLOT(populateBookmarksInAllWindows()));
709 // Add the action to the beginning of the bookmark folder final action list if requsted.
711 bookmarkFolderFinalActionList.prepend(new QPair<QMenu *, QAction *>(menuPointer, editFolderActionPointer));
714 // Add the delete folder action to the menu.
715 QAction *deleteFolderActionPointer = menuPointer->addAction(QIcon::fromTheme(QLatin1String("edit-delete")), i18nc("Delete folder context menu entry", "Delete Folder"), [=]
717 // Create an items to delete list.
718 QList<int>* itemsToDeleteListPointer = new QList<int>;
720 // Add the folder to the list of items to delete if it is not the root folder.
722 itemsToDeleteListPointer->append(folderDatabaseId);
724 // Add the folder contents to the list of items to delete.
725 itemsToDeleteListPointer->append(*BookmarksDatabase::getFolderContentsDatabaseIdsRecursively(folderId));
727 // Instantiate a delete dialog message box.
728 QMessageBox deleteDialogMessageBox;
731 deleteDialogMessageBox.setIcon(QMessageBox::Warning);
733 // Set the window title.
734 deleteDialogMessageBox.setWindowTitle(i18nc("Delete bookmarks dialog title", "Delete Bookmarks"));
737 deleteDialogMessageBox.setText(i18ncp("Delete bookmarks dialog main message", "Delete %1 bookmark item?", "Delete %1 bookmark items?", itemsToDeleteListPointer->count()));
739 // Set the informative text.
740 deleteDialogMessageBox.setInformativeText(i18nc("Delete bookmarks dialog secondary message", "This cannot be undone."));
742 // Set the standard buttons.
743 deleteDialogMessageBox.setStandardButtons(QMessageBox::Yes | QMessageBox::No);
745 // Set the default button.
746 deleteDialogMessageBox.setDefaultButton(QMessageBox::No);
748 // Display the dialog and capture the return value.
749 int returnValue = deleteDialogMessageBox.exec();
751 // Delete the domain if instructed.
752 if (returnValue == QMessageBox::Yes)
754 // Get the parent folder ID.
755 double parentFolderId = BookmarksDatabase::getParentFolderId(folderDatabaseId);
757 // Delete the folder and its contents.
758 for (const int databaseId : *itemsToDeleteListPointer)
759 BookmarksDatabase::deleteBookmark(databaseId);
761 // Update the display order of the bookmarks in the parent folder.
762 BookmarksDatabase::updateFolderContentsDisplayOrder(parentFolderId);
764 // Repopulate the bookmarks.
765 populateBookmarksInAllWindows();
770 // Add the key sequences if this is the root bookmarks menu.
773 // Create the key sequences.
774 QKeySequence ctrlBKeySequence = QKeySequence(i18nc("The add bookmark key sequence.", "Ctrl+B"));
775 QKeySequence metaFKeySequence = QKeySequence(i18nc("The add folder key sequence.", "Meta+F"));
777 // Set the action key sequences.
778 actionCollectionPointer->setDefaultShortcut(addBookmarkActionPointer, ctrlBKeySequence);
779 actionCollectionPointer->setDefaultShortcut(addFolderActionPointer, metaFKeySequence);
782 // Add the actions to the beginning of the bookmark folder final action list if requested.
784 bookmarkFolderFinalActionList.prepend(new QPair<QMenu *, QAction *>(menuPointer, addBookmarkActionPointer));
785 bookmarkFolderFinalActionList.prepend(new QPair<QMenu *, QAction *>(menuPointer, addFolderActionPointer));
786 bookmarkFolderFinalActionList.prepend(new QPair<QMenu *, QAction *>(menuPointer, openFolderInNewTabsActionPointer));
787 bookmarkFolderFinalActionList.prepend(new QPair<QMenu *, QAction *>(menuPointer, openFolderInBackgroundTabsActionPointer));
788 bookmarkFolderFinalActionList.prepend(new QPair<QMenu *, QAction *>(menuPointer, openFolderInNewWindowActionPointer));
789 bookmarkFolderFinalActionList.prepend(new QPair<QMenu *, QAction *>(menuPointer, deleteFolderActionPointer));
793 void BrowserWindow::addOrEditDomainSettings()
795 // Remove the focus from the URL line edit.
796 urlLineEditPointer->clearFocus();
798 // Get the current domain settings name.
799 QString ¤tDomainSettingsName = tabWidgetPointer->getDomainSettingsName();
801 // Run the commands according to the current domain settings status.
802 if (currentDomainSettingsName == QStringLiteral("")) // Domain settings are not currently applied.
804 // Get the current settings status.
805 int javaScriptInt = calculateSettingsInt(javaScriptEnabled, Settings::javaScriptEnabled());
806 int localStorageInt = calculateSettingsInt(localStorageActionPointer->isChecked(), Settings::localStorageEnabled());
807 int domStorageInt = calculateSettingsInt(domStorageActionPointer->isChecked(), Settings::domStorageEnabled());
809 // Get the current user agent string.
810 QString currentUserAgentString = tabWidgetPointer->getCurrentUserAgent();
812 // Get the current user agent database string.
813 QString currentUserAgentDatabaseString = UserAgentHelper::getDatabaseUserAgentNameFromUserAgent(currentUserAgentString);
815 // Initialize the user agent database string.
816 QString userAgentDatabaseString = UserAgentHelper::SYSTEM_DEFAULT_DATABASE;
818 // Replace the user agent database string if the current user agent is not the default.
819 if (currentUserAgentDatabaseString != Settings::userAgent())
820 userAgentDatabaseString = currentUserAgentDatabaseString;
822 // Initialize the zoom factor variables.
823 int zoomFactorInt = DomainsDatabase::SYSTEM_DEFAULT;
825 // Use a custom zoom factor if currently applied. Doubles cannot be reliably compared using `==`, so a mathematical workaround is used.
826 if (abs(currentZoomFactorDouble - defaultZoomFactorDouble ) > 0.01)
827 zoomFactorInt = DomainsDatabase::CUSTOM;
830 DomainsDatabase::addDomain(currentUrl.host(), javaScriptInt, localStorageInt, domStorageInt, userAgentDatabaseString, zoomFactorInt, currentZoomFactorDouble);
832 // Apply the domain settings.
833 tabWidgetPointer->applyDomainSettingsAndReload();
836 // Create the domain settings dialog pointer.
837 DomainSettingsDialog *domainSettingsDialogPointer = new DomainSettingsDialog(this, DomainSettingsDialog::EDIT_DOMAIN, currentDomainSettingsName);
839 // Reload the tabs when domain settings are updated.
840 connect(domainSettingsDialogPointer, SIGNAL(domainSettingsUpdated()), tabWidgetPointer, SLOT(applyDomainSettingsAndReload()));
843 domainSettingsDialogPointer->show();
846 void BrowserWindow::back() const
848 // Remove the focus from the URL line edit.
849 urlLineEditPointer->clearFocus();
852 tabWidgetPointer->back();
855 int BrowserWindow::calculateSettingsInt(const bool settingCurrentlyEnabled, const bool settingEnabledByDefault) const
857 // Return the int that matches the current state.
858 if (settingCurrentlyEnabled == settingEnabledByDefault) // The current system default is used.
859 return DomainsDatabase::SYSTEM_DEFAULT;
860 else if (settingCurrentlyEnabled) // The setting is enabled, which is different from the system default.
861 return DomainsDatabase::ENABLED;
862 else // The setting is disabled, which is different from the system default.
863 return DomainsDatabase::DISABLED;
866 void BrowserWindow::clearUrlLineEditFocus() const
868 // Remove the focus from the URL line edit.
869 urlLineEditPointer->clearFocus();
872 void BrowserWindow::decrementZoom()
874 // Update the current zoom factor.
875 currentZoomFactorDouble = currentZoomFactorDouble - 0.25;
877 // Check to make sure the zoom factor is in the valid range (0.25 to 5.00).
878 if (currentZoomFactorDouble < 0.25)
879 currentZoomFactorDouble = 0.25;
881 // Set the new zoom factor.
882 tabWidgetPointer->applyOnTheFlyZoomFactor(currentZoomFactorDouble);
884 // Update the on-the-fly action text.
885 updateZoomActions(currentZoomFactorDouble);
888 void BrowserWindow::editBookmarks()
890 // Instantiate an edit bookmarks dialog.
891 BookmarksDialog *bookmarksDialogPointer = new BookmarksDialog(this, tabWidgetPointer->getCurrentTabFavoritIcon(), tabWidgetPointer->getCurrentTabTitle(), tabWidgetPointer->getCurrentTabUrl());
893 // Update the displayed bookmarks when edited.
894 connect(bookmarksDialogPointer, SIGNAL(bookmarkUpdated()), this, SLOT(populateBookmarksInAllWindows()));
897 bookmarksDialogPointer->show();
900 void BrowserWindow::escape() const
902 // Process the escape according to the status of the browser.
903 if (fullScreenActionPointer->isChecked()) // Full screen browsing is enabled.
905 // Exit full screen browsing.
906 fullScreenActionPointer->trigger();
908 else if (!findTextLineEditPointer->text().isEmpty()) // Find text is populated.
910 // Clear the find text line edit.
911 findTextLineEditPointer->clear();
913 // Clear the search in the WebEngine.
914 tabWidgetPointer->findText(QStringLiteral(""));
916 else if (findTextLineEditActionPointer->isVisible()) // Find text actions are visible.
918 // Hide the find text actions.
919 hideFindTextActions();
923 void BrowserWindow::findNext() const
925 // Get the find string.
926 const QString findString = findTextLineEditPointer->text();
928 // Search for the text if it is not empty.
929 if (!findString.isEmpty())
930 tabWidgetPointer->findText(findString);
933 void BrowserWindow::findPrevious() const
935 // Get the find string.
936 const QString findString = findTextLineEditPointer->text();
938 // Search for the text if it is not empty.
939 if (!findString.isEmpty())
940 tabWidgetPointer->findPrevious(findString);
943 void BrowserWindow::forward() const
945 // Remove the focus from the URL line edit.
946 urlLineEditPointer->clearFocus();
949 tabWidgetPointer->forward();
952 void BrowserWindow::fullScreenRequested(const bool toggleOn)
954 // Toggle full screen mode.
955 if (toggleOn) // Turn full screen mode on.
957 // Enable full screen mode.
958 fullScreenActionPointer->setFullScreen(window(), true);
960 // Hide the menu bar if specified.
961 if (Settings::fullScreenHideMenuBar())
962 menuBar()->setVisible(false);
964 // Hide the toolbars if specified.
965 if (Settings::fullScreenHideToolBars())
967 navigationToolBarPointer->setVisible(false);
968 urlToolBarPointer->setVisible(false);
969 bookmarksToolBarPointer->setVisible(false);
972 // Hide the tab bar if specified.
973 if (Settings::fullScreenHideTabBar())
974 tabWidgetPointer->setTabBarVisible(false);
976 // Hide the status bar if specified.
977 if (Settings::fullScreenHideStatusBar())
978 statusBar()->setVisible(false);
980 else // Disable full screen browsing mode.
982 // Disable full screen mode.
983 fullScreenActionPointer->setFullScreen(window(), false);
985 // Show the menu bar.
986 menuBar()->setVisible(true);
988 // Show the toolbars.
989 navigationToolBarPointer->setVisible(true);
990 urlToolBarPointer->setVisible(true);
992 // Only show the bookmarks toolbar if it was previously visible.
993 if (bookmarksToolBarIsVisible)
994 bookmarksToolBarPointer->setVisible(true);
997 tabWidgetPointer->setTabBarVisible(true);
999 // Show the status bar.
1000 statusBar()->setVisible(true);
1004 void BrowserWindow::getZoomFactorFromUser()
1006 // Create an OK flag.
1009 // Display a dialog to get the new zoom factor from the user. Format the double to display two decimals and have a 0.25 step.
1010 double newZoomFactorDouble = QInputDialog::getDouble(this, i18nc("The on-the-fly zoom factor dialog title", "On-The-Fly Zoom Factor"),
1011 i18nc("The instruction text of the on-the-fly zoom factor dialog", "Enter a zoom factor between 0.25 and 5.00"),
1012 currentZoomFactorDouble, .025, 5.00, 2, &okClicked, Qt::WindowFlags(), 0.25);
1014 // Update the zoom factor if the user clicked OK.
1017 // Set the new zoom factor.
1018 tabWidgetPointer->applyOnTheFlyZoomFactor(newZoomFactorDouble);
1020 // Update the on-the-fly action text.
1021 updateZoomActions(newZoomFactorDouble);
1025 void BrowserWindow::hideFindTextActions() const
1027 // Hide the find text actions.
1028 findTextLineEditActionPointer->setVisible(false);
1029 findTextLabelActionPointer->setVisible(false);
1030 findNextActionPointer->setVisible(false);
1031 findPreviousActionPointer->setVisible(false);
1032 findCaseSensitiveActionPointer->setVisible(false);
1033 hideFindTextActionPointer->setVisible(false);
1036 void BrowserWindow::home() const
1038 // Remove the focus from the URL line edit.
1039 urlLineEditPointer->clearFocus();
1042 tabWidgetPointer->home();
1045 void BrowserWindow::hideProgressBar() const
1047 // Hide the progress bar.
1048 progressBarPointer->hide();
1050 // Disable and hide the stop action.
1051 stopActionPointer->setEnabled(false);
1052 stopActionPointer->setVisible(false);
1054 // Enable and show the refresh action.
1055 refreshActionPointer->setEnabled(true);
1056 refreshActionPointer->setVisible(true);
1059 void BrowserWindow::incrementZoom()
1061 // Update the current zoom factor.
1062 currentZoomFactorDouble = currentZoomFactorDouble + 0.25;
1064 // Check to make sure the zoom factor is in the valid range (0.25 to 5.00).
1065 if (currentZoomFactorDouble > 5.0)
1066 currentZoomFactorDouble = 5.0;
1068 // Set the new zoom factor.
1069 tabWidgetPointer->applyOnTheFlyZoomFactor(currentZoomFactorDouble);
1071 // Update the on-the-fly action text.
1072 updateZoomActions(currentZoomFactorDouble);
1075 void BrowserWindow::loadUrlFromLineEdit(const QString &url) const
1077 // Remove the focus from the URL line edit.
1078 urlLineEditPointer->clearFocus();
1081 tabWidgetPointer->loadUrlFromLineEdit(url);
1084 void BrowserWindow::newWindow() const
1086 // Create a new browser window.
1087 BrowserWindow *browserWindowPointer = new BrowserWindow();
1089 // Show the new browser window.
1090 browserWindowPointer->show();
1093 void BrowserWindow::populateBookmarksInAllWindows() const
1095 // Get a list of all the registered service names.
1096 QStringList registeredServiceNames = QDBusConnection::sessionBus().interface()->registeredServiceNames().value();
1098 // Get a list of all the Privacy Browser windows, which will be `com.stoutner.privacybrowser-` with the PID appended.
1099 QStringList privacyBrowserServiceNames = registeredServiceNames.filter("com.stoutner.privacybrowser");
1101 // Repopulate the bookmarks in each window.
1102 for (QString privacyBrowserServiceName : privacyBrowserServiceNames)
1104 // Prepare the D-Bus message.
1105 QDBusMessage dBusMessage = QDBusMessage::createMethodCall(privacyBrowserServiceName, "/privacybrowser/MainWindow_1", "com.stoutner.privacybrowser.BrowserWindow", "populateBookmarksInThisWindow");
1108 QDBusConnection::sessionBus().send(dBusMessage);
1112 void BrowserWindow::populateBookmarksInThisWindow()
1114 // Remove all the final bookmark folder menu actions.
1115 for (QPair<QMenu *, QAction *> *bookmarkFolderFinalActionPairPointer : bookmarkFolderFinalActionList)
1117 // Remove the action.
1118 bookmarkFolderFinalActionPairPointer->first->removeAction(bookmarkFolderFinalActionPairPointer->second);
1121 // Remove all the current menu bookmarks.
1122 for (QPair<QMenu *, QAction *> *bookmarkMenuActionPairPointer : bookmarksMenuActionList)
1124 // Remove the bookmark.
1125 bookmarkMenuActionPairPointer->first->removeAction(bookmarkMenuActionPairPointer->second);
1128 // Remove all the current menu subfolders.
1129 for (QPair<QMenu *, QMenu *> *submenuPairPointer : bookmarksMenuSubmenuList)
1131 // Remove the submenu from the parent menu.
1132 submenuPairPointer->first->removeAction(submenuPairPointer->second->menuAction());
1135 // Remove all the current toolbar subfolders.
1136 for (QPair<QMenu *, QAction *> *subfolderActionPairPointer : bookmarksToolBarSubfolderActionList)
1138 // Remove the action from the subfolder.
1139 subfolderActionPairPointer->first->removeAction(subfolderActionPairPointer->second);
1142 // Remove all the current toolbar bookmarks.
1143 for (QAction *bookmarkAction : bookmarksToolBarActionList)
1145 // Remove the bookmark.
1146 bookmarksToolBarPointer->removeAction(bookmarkAction);
1149 // Clear the action lists.
1150 bookmarkFolderFinalActionList.clear();
1151 bookmarksMenuActionList.clear();
1152 bookmarksMenuSubmenuList.clear();
1153 bookmarksToolBarSubfolderActionList.clear();
1154 bookmarksToolBarActionList.clear();
1156 // Populate the bookmarks subfolders, beginning with the root folder (`0`);
1157 populateBookmarksMenuSubfolders(0, bookmarksMenuPointer);
1159 // Populate the bookmarks toolbar.
1160 populateBookmarksToolBar();
1162 // Get a handle for the bookmark toolbar layout.
1163 QLayout *bookmarksToolBarLayoutPointer = bookmarksToolBarPointer->layout();
1165 // Get the count of the bookmarks.
1166 int bookmarkCount = bookmarksToolBarLayoutPointer->count();
1168 // Set the layout of each bookmark to be left aligned.
1169 for(int i = 0; i < bookmarkCount; ++i)
1170 bookmarksToolBarLayoutPointer->itemAt(i)->setAlignment(Qt::AlignLeft);
1172 // Update the bookmarked action.
1173 updateBookmarkedAction();
1176 void BrowserWindow::populateBookmarksMenuSubfolders(const double folderId, QMenu *menuPointer)
1178 // Get the folder contents.
1179 QList<BookmarkStruct> *folderContentsListPointer = BookmarksDatabase::getFolderContents(folderId);
1181 // Populate the bookmarks menu and toolbar.
1182 for (BookmarkStruct bookmarkStruct : *folderContentsListPointer)
1184 // Process the item according to the type.
1185 if (bookmarkStruct.isFolder) // This item is a folder.
1187 // Add a submenu to the menu.
1188 QMenu *submenuPointer = menuPointer->addMenu(bookmarkStruct.favoriteIcon, bookmarkStruct.name);
1190 // Add the submenu to the beginning of the list of menus to be deleted on repopulate.
1191 bookmarksMenuSubmenuList.prepend(new QPair<QMenu *, QMenu *>(menuPointer, submenuPointer));
1193 // Populate any subfolders.
1194 populateBookmarksMenuSubfolders(bookmarkStruct.folderId, submenuPointer);
1196 else // This item is a bookmark.
1198 // Add the bookmark to the menu.
1199 QAction *menuBookmarkActionPointer = menuPointer->addAction(bookmarkStruct.favoriteIcon, bookmarkStruct.name, [=]
1201 // Remove the focus from the URL line edit.
1202 urlLineEditPointer->clearFocus();
1205 tabWidgetPointer->loadUrlFromLineEdit(bookmarkStruct.url);
1209 // Add the actions to the beginning of the list of bookmarks to be deleted on repopulate.
1210 bookmarksMenuActionList.prepend(new QPair<QMenu *, QAction *>(menuPointer, menuBookmarkActionPointer));
1214 // Add the extra items at the bottom of the menu. `true` adds them to the list of actions to be deleted on repopulate.
1215 addBookmarkFolderFinalActions(menuPointer, folderId, true);
1218 void BrowserWindow::populateBookmarksToolBar()
1220 // Get the root folder contents (which has a folder ID of `0`).
1221 QList<BookmarkStruct> *folderContentsListPointer = BookmarksDatabase::getFolderContents(0);
1223 // Populate the bookmarks toolbar.
1224 for (BookmarkStruct bookmarkStruct : *folderContentsListPointer)
1226 // Process the item according to the type.
1227 if (bookmarkStruct.isFolder) // This item is a folder.
1229 // Add the subfolder action.
1230 QAction *toolBarSubfolderActionPointer = bookmarksToolBarPointer->addAction(bookmarkStruct.favoriteIcon, bookmarkStruct.name);
1232 // Add the bookmark database ID to the toolbar action.
1233 toolBarSubfolderActionPointer->setData(bookmarkStruct.databaseId);
1235 // Add the action to the beginning of the list of actions to be deleted on repopulate.
1236 bookmarksToolBarActionList.prepend(toolBarSubfolderActionPointer);
1238 // Create a subfolder menu.
1239 QMenu *subfolderMenuPointer = new QMenu();
1241 // Add the menu to the action.
1242 toolBarSubfolderActionPointer->setMenu(subfolderMenuPointer);
1244 // Add the submenu to the toolbar menu list.
1245 bookmarksToolBarMenuList.append(new QPair<QMenu *, const double>(subfolderMenuPointer, bookmarkStruct.folderId));
1247 // Set the popup mode for the menu.
1248 dynamic_cast<QToolButton *>(bookmarksToolBarPointer->widgetForAction(toolBarSubfolderActionPointer))->setPopupMode(QToolButton::InstantPopup);
1250 // Populate the subfolder.
1251 populateBookmarksToolBarSubfolders(bookmarkStruct.folderId, subfolderMenuPointer);
1253 else // This item is a bookmark.
1255 // Add the bookmark to the toolbar.
1256 QAction *toolBarBookmarkActionPointer = bookmarksToolBarPointer->addAction(bookmarkStruct.favoriteIcon, bookmarkStruct.name, [=]
1258 // Remove the focus from the URL line edit.
1259 urlLineEditPointer->clearFocus();
1262 tabWidgetPointer->loadUrlFromLineEdit(bookmarkStruct.url);
1266 // Add the bookmark database ID to the toolbar action.
1267 toolBarBookmarkActionPointer->setData(bookmarkStruct.databaseId);
1269 // Add the actions to the beginning of the current bookmarks lists.
1270 bookmarksToolBarActionList.prepend(toolBarBookmarkActionPointer);
1274 // Add the extra items to the toolbar folder menus. The first item in the pair is the menu pointer. The second is the folder ID.
1275 for (QPair<QMenu *, const double> *menuAndFolderIdPairPointer : bookmarksToolBarMenuList)
1277 // Populate the final bookmarks menu entries. `true` adds them to the list of actions to be deleted on repopulate.
1278 addBookmarkFolderFinalActions(menuAndFolderIdPairPointer->first, menuAndFolderIdPairPointer->second, true);
1282 void BrowserWindow::populateBookmarksToolBarSubfolders(const double folderId, QMenu *menuPointer)
1284 // Get the folder contents.
1285 QList<BookmarkStruct> *folderContentsListPointer = BookmarksDatabase::getFolderContents(folderId);
1287 // Populate the bookmarks folder.
1288 for (BookmarkStruct bookmarkStruct : *folderContentsListPointer)
1290 // Get the bookmark URL.
1291 QString bookmarkUrl = bookmarkStruct.url;
1293 // Process the item according to the type.
1294 if (bookmarkStruct.isFolder) // This item is a folder.
1296 // Add the subfolder action.
1297 QAction *toolBarSubfolderActionPointer = menuPointer->addAction(bookmarkStruct.favoriteIcon, bookmarkStruct.name);
1299 // Add the action to the beginning of the list of actions to be deleted on repopulate.
1300 bookmarksToolBarSubfolderActionList.prepend(new QPair<QMenu *, QAction *>(menuPointer, toolBarSubfolderActionPointer));
1302 // Create a subfolder menu.
1303 QMenu *subfolderMenuPointer = new QMenu();
1305 // Add the submenu to the action.
1306 toolBarSubfolderActionPointer->setMenu(subfolderMenuPointer);
1308 // Add the submenu to the toolbar menu list.
1309 bookmarksToolBarMenuList.append(new QPair<QMenu *, const double>(subfolderMenuPointer, bookmarkStruct.folderId));
1311 // Populate the subfolder menu.
1312 populateBookmarksToolBarSubfolders(bookmarkStruct.folderId, subfolderMenuPointer);
1314 else // This item is a bookmark.
1316 // Add the bookmark to the folder.
1317 QAction *toolBarBookmarkActionPointer = menuPointer->addAction(bookmarkStruct.favoriteIcon, bookmarkStruct.name, [=]
1319 // Remove the focus from the URL line edit.
1320 urlLineEditPointer->clearFocus();
1323 tabWidgetPointer->loadUrlFromLineEdit(bookmarkUrl);
1327 // Add the bookmark database ID to the toolbar action.
1328 toolBarBookmarkActionPointer->setData(bookmarkStruct.databaseId);
1330 // Add the action to the beginning of the list of actions to be deleted on repopulate.
1331 bookmarksToolBarSubfolderActionList.prepend(new QPair<QMenu *, QAction *>(menuPointer, toolBarBookmarkActionPointer));
1336 void BrowserWindow::refresh() const
1338 // Remove the focus from the URL line edit.
1339 urlLineEditPointer->clearFocus();
1341 // Refresh the web page.
1342 tabWidgetPointer->refresh();
1345 void BrowserWindow::reloadAndBypassCache() const
1347 // Remove the focus from the URL line edit.
1348 urlLineEditPointer->clearFocus();
1350 // Refresh the web page.
1351 tabWidgetPointer->refresh();
1354 void BrowserWindow::showBookmarkContextMenu(const QPoint &point)
1356 // Get the bookmark action.
1357 QAction *bookmarkActionPointer = bookmarksToolBarPointer->actionAt(point);
1359 // Check to see if an action was clicked.
1360 if (bookmarkActionPointer) // An action was clicked.
1362 // Create a bookmark context menu.
1363 QMenu *bookmarkContextMenuPointer = new QMenu();
1365 // Get the database ID from the action.
1366 int databaseId = bookmarkActionPointer->data().toInt();
1368 // Create the menu according to the type.
1369 if (BookmarksDatabase::isFolder(databaseId)) // A folder was clicked.
1371 // Populate the final bookmarks menu entries. `false` does not add the actions to the delete list, as they will be automatically deleted when the menu closes.
1372 addBookmarkFolderFinalActions(bookmarkContextMenuPointer, BookmarksDatabase::getFolderId(databaseId), false);
1374 else // A bookmark was clicked.
1376 // Add the open in new tab action to the menu.
1377 bookmarkContextMenuPointer->addAction(QIcon::fromTheme(QLatin1String("tab-new")), i18nc("Open bookmark in new tab context menu entry", "Open in New Tab"), [=]
1379 // Get the bookmark.
1380 BookmarkStruct *bookmarkStructPointer = BookmarksDatabase::getBookmark(databaseId);
1382 // Open the bookmark in a new tab. `true` removes the URL line edit focus, `true` opens the new tab in an adjacent tab. `false` does not load a background tab.
1383 tabWidgetPointer->addTab(true, true, false, bookmarkStructPointer->url);
1387 // Add the open in background tab action to the menu.
1388 bookmarkContextMenuPointer->addAction(QIcon::fromTheme(QLatin1String("tab-new")), i18nc("Open bookmark in background tab context menu entry", "Open in Background Tab"), [=]
1390 // Get the bookmark.
1391 BookmarkStruct *bookmarkStructPointer = BookmarksDatabase::getBookmark(databaseId);
1393 // Open the bookmark in a new tab. `true` removes the URL line edit focus, `true` opens the new tab in an adjacent tab. `true` loads a background tab.
1394 tabWidgetPointer->addTab(true, true, true, bookmarkStructPointer->url);
1398 // Add the open in new window action to the menu.
1399 bookmarkContextMenuPointer->addAction(QIcon::fromTheme(QLatin1String("window-new")), i18nc("Open bookmark in new window context menu entry", "Open in New Window"), [=]
1401 // Get the bookmark.
1402 BookmarkStruct *bookmarkStructPointer = BookmarksDatabase::getBookmark(databaseId);
1404 // Create a new browser window and load the first URL. `false` indicates it is not the first browser window.
1405 BrowserWindow *browserWindowPointer = new BrowserWindow(false, &bookmarkStructPointer->url);
1407 // Show the new browser window.
1408 browserWindowPointer->show();
1413 bookmarkContextMenuPointer->addSeparator();
1415 // Add the edit action to the menu.
1416 bookmarkContextMenuPointer->addAction(QIcon::fromTheme(QLatin1String("document-edit")), i18nc("Edit bookmark context menu entry", "Edit"), [=]
1418 // Get the current tab favorite icon.
1419 QIcon currentTabFavoriteIcon = tabWidgetPointer->getCurrentTabFavoritIcon();
1421 // Instantiate an edit bookmark dialog.
1422 QDialog *editBookmarkDialogPointer = new EditBookmarkDialog(this, databaseId, currentTabFavoriteIcon);
1425 editBookmarkDialogPointer->show();
1427 // Process bookmark events.
1428 connect(editBookmarkDialogPointer, SIGNAL(bookmarkSaved()), this, SLOT(populateBookmarksInAllWindows()));
1432 // Add the copy URL action to the menu.
1433 bookmarkContextMenuPointer->addAction(QIcon::fromTheme(QLatin1String("edit-copy")), i18nc("Copy bookmark URL context menu entry", "Copy URL"), [=]
1435 // Get the bookmark.
1436 BookmarkStruct *bookmarkStructPointer = BookmarksDatabase::getBookmark(databaseId);
1438 // Get a handle for the clipboard.
1439 QClipboard *clipboard = QGuiApplication::clipboard();
1441 // Place the URL on the keyboard.
1442 clipboard->setText(bookmarkStructPointer->url);
1447 bookmarkContextMenuPointer->addSeparator();
1449 // Add the delete action to the menu.
1450 bookmarkContextMenuPointer->addAction(QIcon::fromTheme(QLatin1String("edit-delete")), i18nc("Delete bookmark context menu entry", "Delete"), [=]
1452 // Get the parent folder ID.
1453 double parentFolderId = BookmarksDatabase::getParentFolderId(databaseId);
1455 // Delete the bookmark.
1456 BookmarksDatabase::deleteBookmark(databaseId);
1458 // Update the display order of the bookmarks in the parent folder.
1459 BookmarksDatabase::updateFolderContentsDisplayOrder(parentFolderId);
1461 // Repopulate the bookmarks.
1462 populateBookmarksInAllWindows();
1467 // Delete the menu from memory when it is closed.
1468 bookmarkContextMenuPointer->setAttribute(Qt::WA_DeleteOnClose);
1470 // Display the context menu.
1471 bookmarkContextMenuPointer->popup(bookmarksToolBarPointer->mapToGlobal(point));
1473 else // The toolbar background was clicked.
1475 // Temporarily set the context menu policy to the default.
1476 bookmarksToolBarPointer->setContextMenuPolicy(Qt::DefaultContextMenu);
1478 // Create a context menu event with the same position.
1479 QContextMenuEvent *contextMenuEventPointer = new QContextMenuEvent(QContextMenuEvent::Mouse, point);
1481 // Send the context menu event to the toolbar.
1482 QCoreApplication::sendEvent(bookmarksToolBarPointer, contextMenuEventPointer);
1484 // Reset the context menu policy.
1485 bookmarksToolBarPointer->setContextMenuPolicy(Qt::CustomContextMenu);
1489 void BrowserWindow::showCookiesDialog()
1491 // Remove the focus from the URL line edit.
1492 urlLineEditPointer->clearFocus();
1494 // Instantiate the cookie settings dialog.
1495 CookiesDialog *cookiesDialogPointer = new CookiesDialog(tabWidgetPointer->getCookieList());
1498 cookiesDialogPointer->show();
1500 // Connect the dialog signals.
1501 connect(cookiesDialogPointer, SIGNAL(addCookie(QNetworkCookie)), tabWidgetPointer, SLOT(addCookieToStore(QNetworkCookie)));
1502 connect(cookiesDialogPointer, SIGNAL(deleteAllCookies()), tabWidgetPointer, SLOT(deleteAllCookies()));
1503 connect(cookiesDialogPointer, SIGNAL(deleteCookie(QNetworkCookie)), tabWidgetPointer, SLOT(deleteCookieFromStore(QNetworkCookie)));
1506 void BrowserWindow::showDomainSettingsDialog()
1508 // Remove the focus from the URL line edit.
1509 urlLineEditPointer->clearFocus();
1511 // Instantiate the domain settings dialog.
1512 DomainSettingsDialog *domainSettingsDialogPointer = new DomainSettingsDialog(this);
1514 // Reload the tabs when domain settings are updated.
1515 connect(domainSettingsDialogPointer, SIGNAL(domainSettingsUpdated()), tabWidgetPointer, SLOT(applyDomainSettingsAndReload()));
1518 domainSettingsDialogPointer->show();
1521 void BrowserWindow::showFilterListsDialog()
1523 // Instantiate the filter lists dialog.
1524 FilterListsDialog *filterListsDialogPointer = new FilterListsDialog(this);
1527 filterListsDialogPointer->show();
1530 void BrowserWindow::showFindTextActions() const
1532 // Show the find text actions.
1533 findTextLineEditActionPointer->setVisible(true);
1534 findTextLabelActionPointer->setVisible(true);
1535 findNextActionPointer->setVisible(true);
1536 findPreviousActionPointer->setVisible(true);
1537 findCaseSensitiveActionPointer->setVisible(true);
1538 hideFindTextActionPointer->setVisible(true);
1540 // Set the focus on the find line edit.
1541 findTextLineEditPointer->setFocus();
1543 // Select all the text in the find line edit.
1544 findTextLineEditPointer->selectAll();
1547 void BrowserWindow::showProgressBar(const int &progress) const
1549 // Set the progress bar value.
1550 progressBarPointer->setValue(progress);
1552 // Show the progress bar.
1553 progressBarPointer->show();
1555 // Disable and hide the refresh action.
1556 refreshActionPointer->setEnabled(false);
1557 refreshActionPointer->setVisible(false);
1559 // Enable and show the stop action.
1560 stopActionPointer->setEnabled(true);
1561 stopActionPointer->setVisible(true);
1564 void BrowserWindow::showRequestsDialog()
1566 // Instantiate the requests dialog.
1567 RequestsDialog *requestsDialogPointer = new RequestsDialog(this, tabWidgetPointer->currentPrivacyWebEngineViewPointer->requestsListPointer);
1570 requestsDialogPointer->show();
1573 void BrowserWindow::showSettingsDialog()
1575 // Get a handle for the KConfig skeleton.
1576 KConfigSkeleton *kConfigSkeletonPointer = Settings::self();
1578 // Instantiate a settings dialog.
1579 SettingsDialog *settingsDialogPointer = new SettingsDialog(this, kConfigSkeletonPointer);
1582 settingsDialogPointer->show();
1584 // TODO. KConfigDialog does not respect expanding size policies. <https://redmine.stoutner.com/issues/823>
1585 //settingsDialogPointer->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding);
1586 //privacySettingsWidgetPointer->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding);
1587 //generalSettingsWidgetPointer->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding);
1588 //settingsDialogPointer->adjustSize();
1590 // Expand the config dialog.
1591 settingsDialogPointer->resize(1000, 500);
1593 // Apply the settings handled by KConfig.
1594 connect(settingsDialogPointer, SIGNAL(spellCheckLanguagesUpdated()), tabWidgetPointer, SLOT(applySpellCheckLanguages()));
1595 connect(settingsDialogPointer, SIGNAL(settingsChanged(QString)), tabWidgetPointer, SLOT(applyApplicationSettings()));
1596 connect(settingsDialogPointer, SIGNAL(settingsChanged(QString)), tabWidgetPointer, SLOT(applyDomainSettingsAndReload()));
1599 QSize BrowserWindow::sizeHint() const
1601 // Return the default window size.
1602 return QSize(1500, 1200);
1605 void BrowserWindow::toggleBookmark()
1607 // Remove the focus from the URL line edit, which will have been focused when the user clicked on the bookmarked icon.
1608 urlLineEditPointer->clearFocus();
1610 // Create or delete the bookmark
1611 if (bookmarkedActionPointer->isChecked()) // The user checked the toggle. Create a bookmark.
1613 // Create a bookmark struct.
1614 BookmarkStruct *bookmarkStructPointer = new BookmarkStruct;
1616 // Populate the bookmark struct.
1617 bookmarkStructPointer->name = tabWidgetPointer->getCurrentTabTitle();
1618 bookmarkStructPointer->url = tabWidgetPointer->getCurrentTabUrl();
1619 bookmarkStructPointer->parentFolderId = 0;
1620 bookmarkStructPointer->favoriteIcon = tabWidgetPointer->getCurrentTabFavoritIcon();
1622 // Add the bookmark.
1623 BookmarksDatabase::addBookmark(bookmarkStructPointer);
1625 else // The user unchecked the toggle. Delete all related bookmarks.
1627 // Delete the bookmarks.
1628 BookmarksDatabase::deleteBookmarks(urlLineEditPointer->text());
1633 // Repopulate the bookmarks.
1634 populateBookmarksInAllWindows();
1637 void BrowserWindow::toggleDeveloperTools() const
1639 // Toggle the developer tools.
1640 tabWidgetPointer->toggleDeveloperTools(developerToolsActionPointer->isChecked());
1643 void BrowserWindow::toggleDomStorage() const
1645 // Remove the focus from the URL line edit.
1646 urlLineEditPointer->clearFocus();
1648 // Toggle DOM storage.
1649 tabWidgetPointer->toggleDomStorage();
1652 void BrowserWindow::toggleFindCaseSensitive() const
1654 // Get the current find string.
1655 const QString findString = findTextLineEditPointer->text();
1657 // Toggle find case sensitive.
1658 tabWidgetPointer->toggleFindCaseSensitive(findString);
1661 void BrowserWindow::toggleJavaScript() const
1663 // Remove the focus from the URL line edit.
1664 urlLineEditPointer->clearFocus();
1666 // Toggle JavaScript.
1667 tabWidgetPointer->toggleJavaScript();
1670 void BrowserWindow::toggleLocalStorage() const
1672 // Remove the focus from the URL line edit.
1673 urlLineEditPointer->clearFocus();
1675 // Toggle local storage.
1676 tabWidgetPointer->toggleLocalStorage();
1679 void BrowserWindow::toggleFullScreen()
1681 // Toggle the full screen status.
1682 fullScreenRequested(fullScreenActionPointer->isChecked());
1685 void BrowserWindow::toggleViewSource() const
1687 // Get the current URL.
1688 QString url = urlLineEditPointer->text();
1691 if (url.startsWith(QLatin1String("view-source:"))) // The source is currently being viewed.
1693 // Remove `view-source:` from the URL.
1694 url = url.remove(0, 12);
1696 else // The source is not currently being viewed.
1698 // Prepend `view-source:` from the URL.
1699 url = url.prepend(QLatin1String("view-source:"));
1703 loadUrlFromLineEdit(url);
1706 void BrowserWindow::toggleViewBookmarksToolBar()
1708 // Store the current status of the bookmarks toolbar, which is used when exiting full screen browsing.
1709 bookmarksToolBarIsVisible = viewBookmarksToolBarActionPointer->isChecked();
1711 // Update the visibility of the bookmarks toolbar.
1712 bookmarksToolBarPointer->setVisible(bookmarksToolBarIsVisible);
1715 void BrowserWindow::toggleViewSourceInNewTab() const
1717 // Get the current URL.
1718 QString url = urlLineEditPointer->text();
1721 if (url.startsWith(QLatin1String("view-source:"))) // The source is currently being viewed.
1723 // Remove `view-source:` from the URL.
1724 url = url.remove(0, 12);
1726 else // The source is not currently being viewed.
1728 // Prepend `view-source:` from the URL.
1729 url = url.prepend(QLatin1String("view-source:"));
1732 // Add the new tab. `true` removes the URL line edit focus, `true` opens the new tab in an adjacent tab. `false` does not open a background tab.
1733 tabWidgetPointer->addTab(true, true, false, url);
1736 void BrowserWindow::updateBookmarkedAction() const
1738 // Update the bookmarked action to reflect the current state.
1739 if (bookmarkedActionPointer->isChecked())
1740 bookmarkedActionPointer->setIcon(QIcon::fromTheme("starred-symbolic"));
1742 bookmarkedActionPointer->setIcon(QIcon::fromTheme("non-starred-symbolic"));
1745 void BrowserWindow::updateRequestsAction(const int blockedRequests) const
1747 // Update the requests action text.
1748 requestsActionPointer->setText(i18nc("Requests action", "Requests - %1 Blocked", blockedRequests));
1751 void BrowserWindow::updateCookiesAction(const int numberOfCookies) const
1753 // Update the cookies action text.
1754 cookiesActionPointer->setText(i18nc("The Cookies action, which also displays the number of cookies", "Cookies - %1", numberOfCookies));
1757 void BrowserWindow::updateDefaultZoomFactor(const double newDefaultZoomFactorDouble)
1759 // Store the new default zoom factor.
1760 defaultZoomFactorDouble = newDefaultZoomFactorDouble;
1763 void BrowserWindow::updateDomStorageAction(const bool &isEnabled) const
1765 // Set the action checked status.
1766 domStorageActionPointer->setChecked(isEnabled);
1769 void BrowserWindow::updateDomainSettingsIndicator(const bool status)
1771 // Set the domain palette according to the status.
1773 urlLineEditPointer->setPalette(positiveBackgroundPalette);
1775 urlLineEditPointer->setPalette(normalBackgroundPalette);
1778 void BrowserWindow::updateFindText(const QString &text, const bool findCaseSensitive) const
1781 findTextLineEditPointer->setText(text);
1783 // Set the find case sensitive action checked status.
1784 findCaseSensitiveActionPointer->setChecked(findCaseSensitive);
1787 void BrowserWindow::updateFindTextResults(const QWebEngineFindTextResult &findTextResult) const
1789 // Update the find text label.
1790 findTextLabelPointer->setText(QStringLiteral(" %1/%2 ").arg(findTextResult.activeMatch()).arg(findTextResult.numberOfMatches()));
1792 // Set the background color according to the find status.
1793 if (findTextLineEditPointer->text().isEmpty())
1794 findTextLineEditPointer->setPalette(normalBackgroundPalette);
1795 else if (findTextResult.numberOfMatches() == 0)
1796 findTextLineEditPointer->setPalette(negativeBackgroundPalette);
1798 findTextLineEditPointer->setPalette(positiveBackgroundPalette);
1801 void BrowserWindow::updateJavaScriptAction(const bool &isEnabled)
1803 // Update the JavaScript status.
1804 javaScriptEnabled = isEnabled;
1806 // Set the icon according to the status.
1807 if (javaScriptEnabled)
1808 javaScriptActionPointer->setIcon(QIcon(QLatin1String(":/icons/javascript-warning.svg")));
1810 javaScriptActionPointer->setIcon(QIcon(QLatin1String(":/icons/privacy-mode.svg")));
1812 // Set the action checked status.
1813 javaScriptActionPointer->setChecked(javaScriptEnabled);
1815 // Update the status of the DOM storage action.
1816 domStorageActionPointer->setEnabled(javaScriptEnabled & localStorageEnabled);
1819 void BrowserWindow::updateLocalStorageAction(const bool &isEnabled)
1821 // Update the local storage status.
1822 localStorageEnabled = isEnabled;
1824 // Update the icon. On Gnome, the toolbar icons don't pick up unless the size is explicit, probably because the toolbar ends up being an intermediate size.
1825 if (localStorageEnabled)
1826 localStorageActionPointer->setIcon(QIcon::fromTheme(QLatin1String("disk-quota-high"), QIcon(QLatin1String("/usr/share/icons/gnome/32x32/actions/document-save-as.png"))));
1828 localStorageActionPointer->setIcon(QIcon::fromTheme(QLatin1String("disk-quota"), QIcon(QLatin1String("/usr/share/icons/gnome/32x32/apps/kfm.png"))));
1830 // Set the action checked status.
1831 localStorageActionPointer->setChecked(localStorageEnabled);
1833 // Update the status of the DOM storage action.
1834 domStorageActionPointer->setEnabled(localStorageEnabled & javaScriptEnabled);
1837 void BrowserWindow::updateSearchEngineActions(const QString &searchEngine, const bool &updateCustomSearchEngineStatus)
1839 // Initialize the custom search engine flag.
1840 bool customSearchEngine = false;
1842 if (searchEngine == "Mojeek") // Mojeek.
1844 // Check the Mojeek user agent action.
1845 searchEngineMojeekActionPointer->setChecked(true);
1847 // Update the search engine menu action icon.
1848 searchEngineMenuActionPointer->setIcon(QIcon::fromTheme(QLatin1String("edit-find")));
1850 // Update the search engine menu action text.
1851 searchEngineMenuActionPointer->setText(i18nc("The main search engine menu action", "Search Engine - Mojeek"));
1853 else if (searchEngine == "Monocles") // Monocles.
1855 // Check the Monocles user agent action.
1856 searchEngineMonoclesActionPointer->setChecked(true);
1858 // Update the search engine menu action icon.
1859 searchEngineMenuActionPointer->setIcon(QIcon::fromTheme(QLatin1String("edit-find")));
1861 // Update the search engine menu action text.
1862 searchEngineMenuActionPointer->setText(i18nc("The main search engine menu action", "Search Engine - Monocles"));
1864 else if (searchEngine == "MetaGer") // MetaGer.
1866 // Check the MetaGer user agent action.
1867 searchEngineMetagerActionPointer->setChecked(true);
1869 // Update the search engine menu action icon.
1870 searchEngineMenuActionPointer->setIcon(QIcon::fromTheme(QLatin1String("edit-find")));
1872 // Update the search engine menu action text.
1873 searchEngineMenuActionPointer->setText(i18nc("The main search engine menu action", "Search Engine - MetaGer"));
1875 else if (searchEngine == "Google") // Google.
1877 // Check the Google user agent action.
1878 searchEngineGoogleActionPointer->setChecked(true);
1880 // Update the search engine menu action icon.
1881 searchEngineMenuActionPointer->setIcon(QIcon::fromTheme(QLatin1String("im-google"), QIcon::fromTheme(QLatin1String("edit-find"))));
1883 // Update the search engine menu action text.
1884 searchEngineMenuActionPointer->setText(i18nc("The main search engine menu action", "Search Engine - Google"));
1886 else if (searchEngine == "Bing") // Bing.
1888 // Check the Bing user agent action.
1889 searchEngineBingActionPointer->setChecked(true);
1891 // Update the search engine menu action icon.
1892 searchEngineMenuActionPointer->setIcon(QIcon::fromTheme(QLatin1String("edit-find")));
1894 // Update the search engine menu action text.
1895 searchEngineMenuActionPointer->setText(i18nc("The main search engine menu action", "Search Engine - Bing"));
1897 else if (searchEngine == "Yahoo") // Yahoo.
1899 // Check the Yahoo user agent action.
1900 searchEngineYahooActionPointer->setChecked(true);
1902 // Update the search engine menu action icon.
1903 searchEngineMenuActionPointer->setIcon(QIcon::fromTheme(QLatin1String("im-yahoo"), QIcon::fromTheme(QLatin1String("edit-find"))));
1905 // Update the search engine menu action text.
1906 searchEngineMenuActionPointer->setText(i18nc("The main search engine menu action", "Search Engine - Yahoo"));
1908 else // Custom search engine.
1910 // Check the user agent.
1911 searchEngineCustomActionPointer->setChecked(true);
1913 // Update the search engine menu action icon.
1914 searchEngineMenuActionPointer->setIcon(QIcon::fromTheme(QLatin1String("edit-find")));
1916 // Update the search engine menu action text.
1917 searchEngineMenuActionPointer->setText(i18nc("The main search engine menu action", "Search Engine - Custom"));
1919 // Set the custom search engine text.
1920 searchEngineCustomActionPointer->setText(searchEngine);
1922 // Set the custom search engine flag.
1923 customSearchEngine = true;
1926 // Update the custom search engine enabled boolean.
1927 if (updateCustomSearchEngineStatus)
1928 customSearchEngineEnabled = customSearchEngine;
1930 // Format the custom search engine.
1931 if (customSearchEngineEnabled)
1933 // Enable the custom search engine.
1934 searchEngineCustomActionPointer->setEnabled(true);
1938 // Disable the custom search engine.
1939 searchEngineCustomActionPointer->setEnabled(false);
1941 // Reset the custom search engine text.
1942 searchEngineCustomActionPointer->setText(i18nc("@action", "Custom"));
1946 void BrowserWindow::updateUrlLineEdit(const QUrl &newUrl)
1948 // Get the new URL string in encoded form, which displays punycode.
1949 QString newUrlString = newUrl.toEncoded();
1951 // Update the view source actions.
1952 if (newUrlString.startsWith(QLatin1String("view-source:"))) // The source is currently being viewed.
1954 // Mark the view source checkbox.
1955 viewSourceActionPointer->setChecked(true);
1957 // Update the view in new tab action text.
1958 viewSourceInNewTabActionPointer->setText(i18nc("View rendered website in new tab action", "View Rendered Website in New Tab"));
1960 else // The source is not currently being viewed.
1962 // Unmark the view source checkbox.
1963 viewSourceActionPointer->setChecked(false);
1965 // Update the view in new tab action text.
1966 viewSourceInNewTabActionPointer->setText(i18nc("View source in new tab action", "View Source in New Tab"));
1969 // Update the URL line edit if it does not have focus.
1970 if (!urlLineEditPointer->hasFocus())
1972 // Update the URL line edit.
1973 urlLineEditPointer->setText(newUrlString);
1975 // Set the bookmarked action status.
1976 bookmarkedActionPointer->setChecked(BookmarksDatabase::isBookmarked(newUrlString));
1978 // Update the bookmarked action.
1979 updateBookmarkedAction();
1981 // Set the focus if the new URL is blank.
1982 if (newUrlString == QStringLiteral(""))
1983 urlLineEditPointer->setFocus();
1986 // Store the current URL.
1987 currentUrl = newUrl;
1990 void BrowserWindow::updateUserAgentActions(const QString &userAgent, const bool &updateCustomUserAgentStatus)
1992 // Initialize the custom user agent flag.
1993 bool customUserAgent = false;
1995 // Check the indicated on-the-fly user agent.
1996 if (userAgent == UserAgentHelper::PRIVACY_BROWSER_USER_AGENT) // Privacy Browser.
1998 // Check the Privacy Browser user agent action.
1999 userAgentPrivacyBrowserActionPointer->setChecked(true);
2001 // Update the user agent menu action icon.
2002 userAgentMenuActionPointer->setIcon(QIcon(":/icons/privacy-mode.svg"));
2004 // Update the user agent menu action text.
2005 userAgentMenuActionPointer->setText(i18nc("The main user agent menu action", "User Agent - Privacy Browser"));
2007 else if (userAgent == TabWidget::webEngineDefaultUserAgent) // WebEngine default.
2009 // check the WebEngine default user agent action.
2010 userAgentWebEngineDefaultActionPointer->setChecked(true);
2012 // Update the user agent menu action icon.
2013 userAgentMenuActionPointer->setIcon(QIcon::fromTheme(QLatin1String("qtlogo"), QIcon::fromTheme(QLatin1String("user-group-properties"), QIcon::fromTheme(QLatin1String("contact-new")))));
2015 // Update the user agent menu action text.
2016 userAgentMenuActionPointer->setText(i18nc("The main user agent menu action", "User Agent - WebEngine default"));
2018 else if (userAgent == UserAgentHelper::FIREFOX_LINUX_USER_AGENT) // Firefox on Linux.
2020 // Check the Firefox on Linux user agent action.
2021 userAgentFirefoxLinuxActionPointer->setChecked(true);
2023 // Update the user agent menu action icon.
2024 userAgentMenuActionPointer->setIcon(QIcon::fromTheme(QLatin1String("firefox-esr"), QIcon::fromTheme(QLatin1String("user-group-properties"), QIcon::fromTheme(QLatin1String("contact-new")))));
2026 // Update the user agent menu action text.
2027 userAgentMenuActionPointer->setText(i18nc("The main user agent menu action", "User Agent - Firefox on Linux"));
2029 else if (userAgent == UserAgentHelper::CHROMIUM_LINUX_USER_AGENT) // Chromium on Linux.
2031 // Check the Chromium on Linux user agent action.
2032 userAgentChromiumLinuxActionPointer->setChecked(true);
2034 // Update the user agent menu action icon.
2035 userAgentMenuActionPointer->setIcon(QIcon::fromTheme(QLatin1String("chromium"), QIcon::fromTheme(QLatin1String("user-group-properties"), QIcon::fromTheme(QLatin1String("contact-new")))));
2037 // Update the user agent menu action text.
2038 userAgentMenuActionPointer->setText(i18nc("The main user agent menu action", "User Agent - Chromium on Linux"));
2040 else if (userAgent == UserAgentHelper::FIREFOX_WINDOWS_USER_AGENT) // Firefox on Windows.
2042 // Check the Firefox on Windows user agent action.
2043 userAgentFirefoxWindowsActionPointer->setChecked(true);
2045 // Update the user agent menu action icon.
2046 userAgentMenuActionPointer->setIcon(QIcon::fromTheme(QLatin1String("firefox-esr"), QIcon::fromTheme(QLatin1String("user-group-properties"), QIcon::fromTheme(QLatin1String("contact-new")))));
2048 // Update the user agent menu action text.
2049 userAgentMenuActionPointer->setText(i18nc("The main user agent menu action", "User Agent - Firefox on Windows"));
2051 else if (userAgent == UserAgentHelper::CHROME_WINDOWS_USER_AGENT) // Chrome on Windows.
2053 // Check the Chrome on Windows user agent action.
2054 userAgentChromeWindowsActionPointer->setChecked(true);
2056 // Update the user agent menu action icon.
2057 userAgentMenuActionPointer->setIcon(QIcon::fromTheme(QLatin1String("chromium"), QIcon::fromTheme(QLatin1String("user-group-properties"), QIcon::fromTheme(QLatin1String("contact-new")))));
2059 // Update the user agent menu action text.
2060 userAgentMenuActionPointer->setText(i18nc("The main user agent menu action", "User Agent - Chrome on Windows"));
2062 else if (userAgent == UserAgentHelper::EDGE_WINDOWS_USER_AGENT) // Edge on Windows.
2064 // Check the Edge on Windows user agent action.
2065 userAgentEdgeWindowsActionPointer->setChecked(true);
2067 // Update the user agent menu action icon.
2068 userAgentMenuActionPointer->setIcon(QIcon::fromTheme(QLatin1String("user-group-properties"), QIcon::fromTheme(QLatin1String("contact-new"))));
2070 // Update the user agent menu action text.
2071 userAgentMenuActionPointer->setText(i18nc("The main user agent menu action", "User Agent - Edge on Windows"));
2073 else if (userAgent == UserAgentHelper::SAFARI_MACOS_USER_AGENT) // Safari on macOS.
2075 // Check the Safari on macOS user agent action.
2076 userAgentSafariMacosActionPointer->setChecked(true);
2078 // Update the user agent menu action icon.
2079 userAgentMenuActionPointer->setIcon(QIcon::fromTheme(QLatin1String("user-group-properties"), QIcon::fromTheme(QLatin1String("contact-new"))));
2081 // Update the user agent menu action text.
2082 userAgentMenuActionPointer->setText(i18nc("The main user agent menu action", "User Agent - Safari on macOS"));
2084 else // Custom user agent.
2086 // Check the user agent.
2087 userAgentCustomActionPointer->setChecked(true);
2089 // Update the user agent menu action icon.
2090 userAgentMenuActionPointer->setIcon(QIcon::fromTheme(QLatin1String("user-group-properties"), QIcon::fromTheme(QLatin1String("contact-new"))));
2092 // Update the user agent menu action text.
2093 userAgentMenuActionPointer->setText(i18nc("The main user agent menu action", "User Agent - Custom"));
2095 // Set the custom user agent text.
2096 userAgentCustomActionPointer->setText(userAgent);
2098 // Set the custom user agent flag.
2099 customUserAgent = true;
2102 // Update the custom user agent enabled boolean.
2103 // This is not done when the current user agent is a custom one but it is temporarially being changed via on-the-fly settings so that the user can switch back to the custom user agent.
2104 if (updateCustomUserAgentStatus)
2105 customUserAgentEnabled = customUserAgent;
2108 // Format the custom user agent.
2109 if (customUserAgentEnabled)
2111 // Enable the custom user agent.
2112 userAgentCustomActionPointer->setEnabled(true);
2116 // Disable the custom user agent.
2117 userAgentCustomActionPointer->setEnabled(false);
2119 // Reset the custom user agent text.
2120 userAgentCustomActionPointer->setText(i18nc("@action", "Custom"));
2124 void BrowserWindow::updateViewBookmarksToolBarCheckbox(const bool visible)
2126 // Update the view bookmarks toolbar checkbox.
2127 viewBookmarksToolBarActionPointer->setChecked(visible);
2129 // Initialize the bookmarks toolbar visibility tracker if Privacy Browser has just launched.
2130 if (bookmarksToolBarUninitialized)
2132 // Set the initialization flag.
2133 bookmarksToolBarUninitialized = false;
2135 // Store the current status of the bookmarks toolbar, which is used when exiting full screen browsing.
2136 bookmarksToolBarIsVisible = visible;
2140 void BrowserWindow::updateWindowTitle(const QString &title)
2142 // Update the window title.
2143 setWindowTitle(title);
2146 void BrowserWindow::updateZoomActions(const double zoomFactorDouble)
2148 // Set the current zoom factor.
2149 currentZoomFactorDouble = zoomFactorDouble;
2151 // Set the status of the default zoom action.
2152 zoomDefaultActionPointer->setEnabled(currentZoomFactorDouble != defaultZoomFactorDouble);
2154 // Set the status of the zoom in action and button.
2155 zoomInActionPointer->setEnabled(currentZoomFactorDouble <= 4.99);
2156 zoomPlusButtonPointer->setEnabled(currentZoomFactorDouble <= 4.99);
2158 // Set the status of the zoom out action and button.
2159 zoomMinusButtonPointer->setEnabled(currentZoomFactorDouble > 0.25);
2160 zoomOutActionPointer->setEnabled(currentZoomFactorDouble > 0.25);
2163 // Update the zoom factor action text, formatting the double with 2 decimal places. `0` specifies no extra field width. `'0'` sets the format to not use scientific notation.
2164 zoomFactorActionPointer->setText(ki18nc("The zoom factor action", "Zoom Factor - %1").subs(zoomFactorDouble, 0, '0', 2).toString());
2166 // Update the status bar zoom factor label.
2167 currentZoomButtonPointer->setText(ki18nc("The status bar zoom, which is just the formatted zoom factor", "%1").subs(zoomFactorDouble, 0, '0', 2).toString());
2170 void BrowserWindow::zoomDefault()
2172 // Set the new zoom factor.
2173 tabWidgetPointer->applyOnTheFlyZoomFactor(defaultZoomFactorDouble);
2175 // Update the on-the-fly action text.
2176 updateZoomActions(defaultZoomFactorDouble);