Skip to content

Commit

Permalink
Deduplicate open tab suggestions and internal pages
Browse files Browse the repository at this point in the history
  • Loading branch information
mallexxx committed Dec 18, 2024
1 parent 1da7874 commit d44ab67
Show file tree
Hide file tree
Showing 4 changed files with 37 additions and 12 deletions.
15 changes: 11 additions & 4 deletions DuckDuckGo/NavigationBar/View/AddressBarTextField.swift
Original file line number Diff line number Diff line change
Expand Up @@ -370,7 +370,11 @@ final class AddressBarTextField: NSTextField {
PixelKit.fire(autocompletePixel)
}

if case .openTab(let title, url: let url) = suggestion {
if case .internalPage(title: let title, url: let url) = suggestion,
url == .bookmarks || url.isSettingsURL {
// when choosing an internal page suggestion preffer already open matching tab
switchTo(OpenTab(title: title, url: url))
} else if case .openTab(let title, url: let url) = suggestion {
switchTo(OpenTab(title: title, url: url))
} else if NSApp.isCommandPressed {
openNew(NSApp.isOptionPressed ? .window : .tab, selected: NSApp.isShiftPressed, suggestion: suggestion)
Expand Down Expand Up @@ -489,8 +493,12 @@ final class AddressBarTextField: NSTextField {
}

private func switchTo(_ tab: OpenTab) {
if let selectedTabViewModel = tabCollectionViewModel.selectedTabViewModel,
let selectionIndex = tabCollectionViewModel.selectionIndex,
let selectedTabViewModel = tabCollectionViewModel.selectedTabViewModel
let selectionIndex = tabCollectionViewModel.selectionIndex

WindowControllersManager.shared.show(url: tab.url, source: .switchToOpenTab, newTab: true /* in case not found */)

if let selectedTabViewModel, let selectionIndex,
case .newtab = selectedTabViewModel.tab.content {
// close tab with "new tab" page open
tabCollectionViewModel.remove(at: selectionIndex)
Expand All @@ -500,7 +508,6 @@ final class AddressBarTextField: NSTextField {
window.performClose(self)
}
}
WindowControllersManager.shared.show(url: tab.url, source: .switchToOpenTab, newTab: false)
}

private func makeUrl(suggestion: Suggestion?, stringValueWithoutSuffix: String, completion: @escaping (URL?, String, Bool) -> Void) {
Expand Down
19 changes: 14 additions & 5 deletions DuckDuckGo/Suggestions/Model/SuggestionContainer.swift
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,7 @@
// limitations under the License.
//

import BrowserServicesKit
import Combine
import Common
import Foundation
Expand All @@ -35,6 +36,7 @@ final class SuggestionContainer {
private let historyCoordinating: HistoryCoordinating
private let bookmarkManager: BookmarkManager
private let startupPreferences: StartupPreferences
private let featureFlagger: FeatureFlagger
private let loading: SuggestionLoading

// Used for presenting the same suggestions after the removal of the local suggestion
Expand All @@ -44,11 +46,12 @@ final class SuggestionContainer {

fileprivate let suggestionsURLSession = URLSession(configuration: .ephemeral)

init(openTabsProvider: @escaping OpenTabsProvider, suggestionLoading: SuggestionLoading, historyCoordinating: HistoryCoordinating, bookmarkManager: BookmarkManager, startupPreferences: StartupPreferences = .shared) {
init(openTabsProvider: @escaping OpenTabsProvider, suggestionLoading: SuggestionLoading, historyCoordinating: HistoryCoordinating, bookmarkManager: BookmarkManager, startupPreferences: StartupPreferences = .shared, featureFlagger: FeatureFlagger = NSApp.delegateTyped.featureFlagger) {
self.openTabsProvider = openTabsProvider
self.bookmarkManager = bookmarkManager
self.historyCoordinating = historyCoordinating
self.startupPreferences = startupPreferences
self.featureFlagger = featureFlagger
self.loading = suggestionLoading
}

Expand Down Expand Up @@ -98,11 +101,17 @@ final class SuggestionContainer {
{ @MainActor in
let selectedTab = WindowControllersManager.shared.selectedTab
let openTabViewModels = WindowControllersManager.shared.allTabViewModels(for: burnerMode)
var usedUrls = Set<String>() // deduplicate
return openTabViewModels.compactMap { model in
guard model.tab !== selectedTab, model.tab.content.isUrl else { return nil }
return model.tab.content.userEditableUrl.map { url in
OpenTab(title: model.title, url: url)
}
guard model.tab !== selectedTab,
model.tab.content.isUrl
|| model.tab.content.urlForWebView?.isSettingsURL == true
|| model.tab.content.urlForWebView == .bookmarks,
let url = model.tab.content.userEditableUrl,
url != selectedTab?.content.userEditableUrl, // doesn‘t match currently selected
usedUrls.insert(url.absoluteString).inserted == true /* if did not contain */ else { return nil }

return OpenTab(title: model.title, url: url)
}
}
}
Expand Down
6 changes: 4 additions & 2 deletions DuckDuckGo/Suggestions/ViewModel/SuggestionViewModel.swift
Original file line number Diff line number Diff line change
Expand Up @@ -181,9 +181,11 @@ struct SuggestionViewModel: Equatable {
return .favoritedBookmarkSuggestion
case .unknown:
return .web
case .internalPage(title: _, url: let url) where url == .bookmarks:
case .internalPage(title: _, url: let url) where url == .bookmarks,
.openTab(title: _, url: let url) where url == .bookmarks:
return .bookmarksFolder
case .internalPage(title: _, url: let url) where url.isSettingsURL:
case .internalPage(title: _, url: let url) where url.isSettingsURL,
.openTab(title: _, url: let url) where url.isSettingsURL:
return .settingsMulticolor16
case .internalPage(title: _, url: let url):
guard url == URL(string: StartupPreferences.shared.formattedCustomHomePageURL) else { return nil }
Expand Down
9 changes: 8 additions & 1 deletion DuckDuckGo/Windows/View/WindowControllersManager.swift
Original file line number Diff line number Diff line change
Expand Up @@ -215,10 +215,17 @@ extension WindowControllersManager {
// prefer current main window
guard windowIdx == 0 || windowController !== mainWindowController else { continue }
let tabCollectionViewModel = windowController.mainViewController.tabCollectionViewModel
guard let index = tabCollectionViewModel.indexInAllTabs(where: { $0.content.urlForWebView == url }) else { continue }
guard let index = tabCollectionViewModel.indexInAllTabs(where: {
$0.content.urlForWebView == url || (url.isSettingsURL && $0.content.urlForWebView?.isSettingsURL == true)
}) else { continue }

windowController.window?.makeKeyAndOrderFront(self)
tabCollectionViewModel.select(at: index)
if let tab = tabCollectionViewModel.tabViewModel(at: index)?.tab,
tab.content.urlForWebView != url {
// navigate to another settings pane
tab.setContent(.contentFromURL(url, source: .switchToOpenTab))
}

return true
}
Expand Down

0 comments on commit d44ab67

Please sign in to comment.