forked from zelo72/mastodon-ios
feat: add keyboard commands for discovery news table
This commit is contained in:
parent
fe93c8b4f7
commit
a957c8bb73
|
@ -150,7 +150,7 @@ extension DiscoveryHashtagsViewController: TableViewControllerNavigateable {
|
|||
navigateToTag(direction: direction, indexPath: indexPathForSelectedRow)
|
||||
} else {
|
||||
// set first visible item selected
|
||||
navigateToFirstVisibleStatus()
|
||||
navigateToFirstVisibleTag()
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -185,7 +185,7 @@ extension DiscoveryHashtagsViewController: TableViewControllerNavigateable {
|
|||
tableView.selectRow(at: indexPath, animated: true, scrollPosition: scrollPosition)
|
||||
}
|
||||
|
||||
private func navigateToFirstVisibleStatus() {
|
||||
private func navigateToFirstVisibleTag() {
|
||||
guard let indexPathsForVisibleRows = tableView.indexPathsForVisibleRows else { return }
|
||||
guard let diffableDataSource = viewModel.diffableDataSource else { return }
|
||||
|
||||
|
|
|
@ -131,3 +131,99 @@ extension DiscoveryNewsViewController: ScrollViewContainer {
|
|||
tableView
|
||||
}
|
||||
}
|
||||
|
||||
extension DiscoveryNewsViewController {
|
||||
override var keyCommands: [UIKeyCommand]? {
|
||||
return navigationKeyCommands
|
||||
}
|
||||
}
|
||||
|
||||
extension DiscoveryNewsViewController: TableViewControllerNavigateable {
|
||||
|
||||
func navigate(direction: TableViewNavigationDirection) {
|
||||
if let indexPathForSelectedRow = tableView.indexPathForSelectedRow {
|
||||
// navigate up/down on the current selected item
|
||||
navigateToLink(direction: direction, indexPath: indexPathForSelectedRow)
|
||||
} else {
|
||||
// set first visible item selected
|
||||
navigateToFirstVisibleLink()
|
||||
}
|
||||
}
|
||||
|
||||
private func navigateToLink(direction: TableViewNavigationDirection, indexPath: IndexPath) {
|
||||
guard let diffableDataSource = viewModel.diffableDataSource else { return }
|
||||
let items = diffableDataSource.snapshot().itemIdentifiers
|
||||
guard let selectedItem = diffableDataSource.itemIdentifier(for: indexPath),
|
||||
let selectedItemIndex = items.firstIndex(of: selectedItem) else {
|
||||
return
|
||||
}
|
||||
|
||||
let _navigateToItem: DiscoveryItem? = {
|
||||
var index = selectedItemIndex
|
||||
while 0..<items.count ~= index {
|
||||
index = {
|
||||
switch direction {
|
||||
case .up: return index - 1
|
||||
case .down: return index + 1
|
||||
}
|
||||
}()
|
||||
guard 0..<items.count ~= index else { return nil }
|
||||
let item = items[index]
|
||||
|
||||
guard Self.validNavigateableItem(item) else { continue }
|
||||
return item
|
||||
}
|
||||
return nil
|
||||
}()
|
||||
|
||||
guard let item = _navigateToItem, let indexPath = diffableDataSource.indexPath(for: item) else { return }
|
||||
let scrollPosition: UITableView.ScrollPosition = overrideNavigationScrollPosition ?? Self.navigateScrollPosition(tableView: tableView, indexPath: indexPath)
|
||||
tableView.selectRow(at: indexPath, animated: true, scrollPosition: scrollPosition)
|
||||
}
|
||||
|
||||
private func navigateToFirstVisibleLink() {
|
||||
guard let indexPathsForVisibleRows = tableView.indexPathsForVisibleRows else { return }
|
||||
guard let diffableDataSource = viewModel.diffableDataSource else { return }
|
||||
|
||||
var visibleItems: [DiscoveryItem] = indexPathsForVisibleRows.sorted().compactMap { indexPath in
|
||||
guard let item = diffableDataSource.itemIdentifier(for: indexPath) else { return nil }
|
||||
guard Self.validNavigateableItem(item) else { return nil }
|
||||
return item
|
||||
}
|
||||
if indexPathsForVisibleRows.first?.row != 0, visibleItems.count > 1 {
|
||||
// drop first when visible not the first cell of table
|
||||
visibleItems.removeFirst()
|
||||
}
|
||||
guard let item = visibleItems.first, let indexPath = diffableDataSource.indexPath(for: item) else { return }
|
||||
let scrollPosition: UITableView.ScrollPosition = overrideNavigationScrollPosition ?? Self.navigateScrollPosition(tableView: tableView, indexPath: indexPath)
|
||||
tableView.selectRow(at: indexPath, animated: true, scrollPosition: scrollPosition)
|
||||
}
|
||||
|
||||
static func validNavigateableItem(_ item: DiscoveryItem) -> Bool {
|
||||
switch item {
|
||||
case .link:
|
||||
return true
|
||||
default:
|
||||
return false
|
||||
}
|
||||
}
|
||||
|
||||
func open() {
|
||||
guard let indexPathForSelectedRow = tableView.indexPathForSelectedRow else { return }
|
||||
guard let diffableDataSource = viewModel.diffableDataSource else { return }
|
||||
guard let item = diffableDataSource.itemIdentifier(for: indexPathForSelectedRow) else { return }
|
||||
|
||||
guard case let .link(link) = item else { return }
|
||||
guard let url = URL(string: link.url) else { return }
|
||||
coordinator.present(
|
||||
scene: .safari(url: url),
|
||||
from: self,
|
||||
transition: .safariPresent(animated: true, completion: nil)
|
||||
)
|
||||
}
|
||||
|
||||
func navigateKeyCommandHandlerRelay(_ sender: UIKeyCommand) {
|
||||
navigateKeyCommandHandler(sender)
|
||||
}
|
||||
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue