diff options
| -rw-r--r-- | ios/MullvadTypes/RelayLocation.swift | 2 | ||||
| -rw-r--r-- | ios/MullvadVPN.xcodeproj/project.pbxproj | 8 | ||||
| -rw-r--r-- | ios/MullvadVPN.xcodeproj/project.xcworkspace/xcshareddata/swiftpm/Package.resolved | 22 | ||||
| -rw-r--r-- | ios/MullvadVPN/View controllers/SelectLocation/AllLocationDataSource.swift | 68 | ||||
| -rw-r--r-- | ios/MullvadVPN/View controllers/SelectLocation/CustomListsDataSource.swift | 6 | ||||
| -rw-r--r-- | ios/MullvadVPN/View controllers/SelectLocation/LocationCellFactory.swift | 4 | ||||
| -rw-r--r-- | ios/MullvadVPN/View controllers/SelectLocation/LocationCellViewModel.swift | 2 | ||||
| -rw-r--r-- | ios/MullvadVPN/View controllers/SelectLocation/LocationDataSource.swift | 155 | ||||
| -rw-r--r-- | ios/MullvadVPN/View controllers/SelectLocation/LocationDataSourceProtocol.swift | 10 | ||||
| -rw-r--r-- | ios/MullvadVPN/View controllers/SelectLocation/SelectLocationSection.swift (renamed from ios/MullvadVPN/View controllers/SelectLocation/SelectLocationGroup.swift) | 6 |
10 files changed, 154 insertions, 129 deletions
diff --git a/ios/MullvadTypes/RelayLocation.swift b/ios/MullvadTypes/RelayLocation.swift index 3018d157c4..b797e69d3c 100644 --- a/ios/MullvadTypes/RelayLocation.swift +++ b/ios/MullvadTypes/RelayLocation.swift @@ -63,7 +63,7 @@ public enum RelayLocation: Codable, Hashable, CustomDebugStringConvertible { } /// A list of `RelayLocation` items preceding the given one in the relay tree - public var ascendants: [RelayLocation] { + public var ancestors: [RelayLocation] { switch self { case let .hostname(country, city, _): return [.country(country), .city(country, city)] diff --git a/ios/MullvadVPN.xcodeproj/project.pbxproj b/ios/MullvadVPN.xcodeproj/project.pbxproj index 888d2782ac..6495711e90 100644 --- a/ios/MullvadVPN.xcodeproj/project.pbxproj +++ b/ios/MullvadVPN.xcodeproj/project.pbxproj @@ -792,7 +792,7 @@ F050AE4C2B70D5A7003F4EDB /* SelectLocationNode.swift in Sources */ = {isa = PBXBuildFile; fileRef = F050AE4B2B70D5A7003F4EDB /* SelectLocationNode.swift */; }; F050AE4E2B70D7F8003F4EDB /* LocationCellViewModel.swift in Sources */ = {isa = PBXBuildFile; fileRef = F050AE4D2B70D7F8003F4EDB /* LocationCellViewModel.swift */; }; F050AE502B70DC4F003F4EDB /* SelectLocationNodeProtocol.swift in Sources */ = {isa = PBXBuildFile; fileRef = F050AE4F2B70DC4F003F4EDB /* SelectLocationNodeProtocol.swift */; }; - F050AE522B70DFC0003F4EDB /* SelectLocationGroup.swift in Sources */ = {isa = PBXBuildFile; fileRef = F050AE512B70DFC0003F4EDB /* SelectLocationGroup.swift */; }; + F050AE522B70DFC0003F4EDB /* SelectLocationSection.swift in Sources */ = {isa = PBXBuildFile; fileRef = F050AE512B70DFC0003F4EDB /* SelectLocationSection.swift */; }; F050AE5E2B739A73003F4EDB /* LocationDataSourceProtocol.swift in Sources */ = {isa = PBXBuildFile; fileRef = F050AE5D2B739A73003F4EDB /* LocationDataSourceProtocol.swift */; }; F050AE602B73A41E003F4EDB /* AllLocationDataSource.swift in Sources */ = {isa = PBXBuildFile; fileRef = F050AE5F2B73A41E003F4EDB /* AllLocationDataSource.swift */; }; F050AE622B74DBAC003F4EDB /* CustomListsDataSource.swift in Sources */ = {isa = PBXBuildFile; fileRef = F050AE612B74DBAC003F4EDB /* CustomListsDataSource.swift */; }; @@ -1908,7 +1908,7 @@ F050AE4B2B70D5A7003F4EDB /* SelectLocationNode.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = SelectLocationNode.swift; sourceTree = "<group>"; }; F050AE4D2B70D7F8003F4EDB /* LocationCellViewModel.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = LocationCellViewModel.swift; sourceTree = "<group>"; }; F050AE4F2B70DC4F003F4EDB /* SelectLocationNodeProtocol.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = SelectLocationNodeProtocol.swift; sourceTree = "<group>"; }; - F050AE512B70DFC0003F4EDB /* SelectLocationGroup.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = SelectLocationGroup.swift; sourceTree = "<group>"; }; + F050AE512B70DFC0003F4EDB /* SelectLocationSection.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = SelectLocationSection.swift; sourceTree = "<group>"; }; F050AE5D2B739A73003F4EDB /* LocationDataSourceProtocol.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = LocationDataSourceProtocol.swift; sourceTree = "<group>"; }; F050AE5F2B73A41E003F4EDB /* AllLocationDataSource.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = AllLocationDataSource.swift; sourceTree = "<group>"; }; F050AE612B74DBAC003F4EDB /* CustomListsDataSource.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = CustomListsDataSource.swift; sourceTree = "<group>"; }; @@ -2345,7 +2345,7 @@ 583DA21325FA4B5C00318683 /* LocationDataSource.swift */, F050AE5D2B739A73003F4EDB /* LocationDataSourceProtocol.swift */, 5888AD82227B11080051EB06 /* SelectLocationCell.swift */, - F050AE512B70DFC0003F4EDB /* SelectLocationGroup.swift */, + F050AE512B70DFC0003F4EDB /* SelectLocationSection.swift */, F050AE4B2B70D5A7003F4EDB /* SelectLocationNode.swift */, F050AE4F2B70DC4F003F4EDB /* SelectLocationNodeProtocol.swift */, 5888AD86227B17950051EB06 /* SelectLocationViewController.swift */, @@ -5213,7 +5213,7 @@ 586C0D912B03D8A400E7CDD7 /* AccessMethodHeaderFooterReuseIdentifier.swift in Sources */, F050AE4C2B70D5A7003F4EDB /* SelectLocationNode.swift in Sources */, 7A2960F62A963F7500389B82 /* AlertCoordinator.swift in Sources */, - F050AE522B70DFC0003F4EDB /* SelectLocationGroup.swift in Sources */, + F050AE522B70DFC0003F4EDB /* SelectLocationSection.swift in Sources */, 063687BA28EB234F00BE7161 /* PacketTunnelTransport.swift in Sources */, A9C342C12ACC37E30045F00E /* TunnelStatusBlockObserver.swift in Sources */, 587425C12299833500CA2045 /* RootContainerViewController.swift in Sources */, diff --git a/ios/MullvadVPN.xcodeproj/project.xcworkspace/xcshareddata/swiftpm/Package.resolved b/ios/MullvadVPN.xcodeproj/project.xcworkspace/xcshareddata/swiftpm/Package.resolved new file mode 100644 index 0000000000..02691892fe --- /dev/null +++ b/ios/MullvadVPN.xcodeproj/project.xcworkspace/xcshareddata/swiftpm/Package.resolved @@ -0,0 +1,22 @@ +{ + "pins" : [ + { + "identity" : "swift-log", + "kind" : "remoteSourceControl", + "location" : "https://github.com/apple/swift-log.git", + "state" : { + "revision" : "173f567a2dfec11d74588eea82cecea555bdc0bc", + "version" : "1.4.0" + } + }, + { + "identity" : "wireguard-apple", + "kind" : "remoteSourceControl", + "location" : "https://github.com/mullvad/wireguard-apple.git", + "state" : { + "revision" : "11a00c20dc03f2751db47e94f585c0778c7bde82" + } + } + ], + "version" : 2 +} diff --git a/ios/MullvadVPN/View controllers/SelectLocation/AllLocationDataSource.swift b/ios/MullvadVPN/View controllers/SelectLocation/AllLocationDataSource.swift index 0d4c6b9bce..33bfe57593 100644 --- a/ios/MullvadVPN/View controllers/SelectLocation/AllLocationDataSource.swift +++ b/ios/MullvadVPN/View controllers/SelectLocation/AllLocationDataSource.swift @@ -15,52 +15,50 @@ class AllLocationDataSource: LocationDataSourceProtocol { private var locationList = [RelayLocation]() func search(by text: String) -> [RelayLocation] { - if text.isEmpty { + guard !text.isEmpty else { return locationList - } else { - var filteredLocations: [RelayLocation] = [] - locationList.forEach { location in - guard let countryNode = nodeByLocation[location] else { return } - countryNode.showsChildren = false + } - if text.isEmpty || countryNode.displayName.fuzzyMatch(text) { - filteredLocations.append(countryNode.location) - } + var filteredLocations: [RelayLocation] = [] + locationList.forEach { location in + guard let countryNode = nodeByLocation[location] else { return } + countryNode.showsChildren = false - for cityNode in countryNode.children { - cityNode.showsChildren = false + if countryNode.displayName.fuzzyMatch(text) { + filteredLocations.append(countryNode.location) + } - let relaysContainSearchString = cityNode.children - .contains(where: { $0.displayName.fuzzyMatch(text) }) + countryNode.children.forEach { cityNode in + cityNode.showsChildren = false - if cityNode.displayName.fuzzyMatch(text) || relaysContainSearchString { - if !filteredLocations.contains(where: { $0 == countryNode.location }) { - filteredLocations.append(countryNode.location) - } + let relaysContainSearchString = cityNode.children + .contains(where: { $0.displayName.fuzzyMatch(text) }) - filteredLocations.append(cityNode.location) - countryNode.showsChildren = true + if cityNode.displayName.fuzzyMatch(text) || relaysContainSearchString { + if !filteredLocations.contains(countryNode.location) { + filteredLocations.append(countryNode.location) + } - if relaysContainSearchString { - cityNode.children.map { $0.location }.forEach { - filteredLocations.append($0) - } - cityNode.showsChildren = true - } + filteredLocations.append(cityNode.location) + countryNode.showsChildren = true + + if relaysContainSearchString { + filteredLocations.append(contentsOf: cityNode.children.map { $0.location }) + cityNode.showsChildren = true } } } - - return filteredLocations } + + return filteredLocations } func reload( - _ response: MullvadREST.REST.ServerRelaysResponse, - relays: [MullvadREST.REST.ServerRelay] + _ response: REST.ServerRelaysResponse, + relays: [REST.ServerRelay] ) -> [RelayLocation] { nodeByLocation.removeAll() - let rootNode = self.makeRootNode(name: SelectLocationGroup.allLocations.description) + let rootNode = self.makeRootNode(name: SelectLocationSection.allLocations.description) for relay in relays { guard case let .city(countryCode, cityCode) = RelayLocation(dashSeparatedString: relay.location), @@ -68,22 +66,22 @@ class AllLocationDataSource: LocationDataSourceProtocol { let relayLocation = RelayLocation.hostname(countryCode, cityCode, relay.hostname) - for ascendantOrSelf in relayLocation.ascendants + [relayLocation] { - guard !nodeByLocation.keys.contains(ascendantOrSelf) else { + for ancestorOrSelf in relayLocation.ancestors + [relayLocation] { + guard !nodeByLocation.keys.contains(ancestorOrSelf) else { continue } // Maintain the `showsChildren` state when transitioning between relay lists - let wasShowingChildren = nodeByLocation[ascendantOrSelf]?.showsChildren ?? false + let wasShowingChildren = nodeByLocation[ancestorOrSelf]?.showsChildren ?? false let node = createNode( root: rootNode, - ascendantOrSelf: ascendantOrSelf, + ancestorOrSelf: ancestorOrSelf, serverLocation: serverLocation, relay: relay, wasShowingChildren: wasShowingChildren ) - nodeByLocation[ascendantOrSelf] = node + nodeByLocation[ancestorOrSelf] = node } } diff --git a/ios/MullvadVPN/View controllers/SelectLocation/CustomListsDataSource.swift b/ios/MullvadVPN/View controllers/SelectLocation/CustomListsDataSource.swift index 25df241bef..897e68b9c3 100644 --- a/ios/MullvadVPN/View controllers/SelectLocation/CustomListsDataSource.swift +++ b/ios/MullvadVPN/View controllers/SelectLocation/CustomListsDataSource.swift @@ -15,12 +15,12 @@ class CustomListsDataSource: LocationDataSourceProtocol { private var locationList = [RelayLocation]() func search(by text: String) -> [RelayLocation] { - return [] + [] } func reload( - _ response: MullvadREST.REST.ServerRelaysResponse, - relays: [MullvadREST.REST.ServerRelay] + _ response: REST.ServerRelaysResponse, + relays: [REST.ServerRelay] ) -> [RelayLocation] { locationList } diff --git a/ios/MullvadVPN/View controllers/SelectLocation/LocationCellFactory.swift b/ios/MullvadVPN/View controllers/SelectLocation/LocationCellFactory.swift index 6e98f1f729..5151752d09 100644 --- a/ios/MullvadVPN/View controllers/SelectLocation/LocationCellFactory.swift +++ b/ios/MullvadVPN/View controllers/SelectLocation/LocationCellFactory.swift @@ -10,7 +10,7 @@ import MullvadTypes import UIKit protocol LocationCellEventHandler { - func collapseCell(for item: LocationCellViewModel) + func toggleCell(for item: LocationCellViewModel) func node(for item: LocationCellViewModel) -> SelectLocationNode? } @@ -48,7 +48,7 @@ final class LocationCellFactory: CellFactoryProtocol { cell.showsCollapseControl = node.isCollapsible cell.isExpanded = node.showsChildren cell.didCollapseHandler = { [weak self] _ in - self?.delegate?.collapseCell(for: item) + self?.delegate?.toggleCell(for: item) } } } diff --git a/ios/MullvadVPN/View controllers/SelectLocation/LocationCellViewModel.swift b/ios/MullvadVPN/View controllers/SelectLocation/LocationCellViewModel.swift index c90e504442..2b27f8e0ed 100644 --- a/ios/MullvadVPN/View controllers/SelectLocation/LocationCellViewModel.swift +++ b/ios/MullvadVPN/View controllers/SelectLocation/LocationCellViewModel.swift @@ -9,6 +9,6 @@ import MullvadTypes struct LocationCellViewModel: Hashable { - let group: SelectLocationGroup + let group: SelectLocationSection let location: RelayLocation } diff --git a/ios/MullvadVPN/View controllers/SelectLocation/LocationDataSource.swift b/ios/MullvadVPN/View controllers/SelectLocation/LocationDataSource.swift index 334c051f81..1a026e54e9 100644 --- a/ios/MullvadVPN/View controllers/SelectLocation/LocationDataSource.swift +++ b/ios/MullvadVPN/View controllers/SelectLocation/LocationDataSource.swift @@ -11,11 +11,11 @@ import MullvadREST import MullvadTypes import UIKit -final class LocationDataSource: UITableViewDiffableDataSource<SelectLocationGroup, LocationCellViewModel> { +final class LocationDataSource: UITableViewDiffableDataSource<SelectLocationSection, LocationCellViewModel> { private var currentSearchString = "" private let tableView: UITableView private let locationCellFactory: LocationCellFactory - private var datasources: [LocationDataSourceProtocol] = [] + private var dataSources: [LocationDataSourceProtocol] = [] var selectedRelayLocation: LocationCellViewModel? var didSelectRelayLocation: ((RelayLocation) -> Void)? @@ -26,12 +26,12 @@ final class LocationDataSource: UITableViewDiffableDataSource<SelectLocationGrou customLists: LocationDataSourceProtocol ) { self.tableView = tableView - self.datasources.append(customLists) - self.datasources.append(allLocations) + self.dataSources.append(customLists) + self.dataSources.append(allLocations) let locationCellFactory = LocationCellFactory( tableView: tableView, - reuseIdentifier: SelectLocationGroup.Cell.locationCell.reuseIdentifier + reuseIdentifier: SelectLocationSection.Cell.locationCell.reuseIdentifier ) self.locationCellFactory = locationCellFactory @@ -51,11 +51,11 @@ final class LocationDataSource: UITableViewDiffableDataSource<SelectLocationGrou return RelaySelector.relayMatchesFilter(relay, filter: filter) } var list: [[LocationCellViewModel]] = [] - for section in 0 ..< datasources.count { + for section in 0 ..< dataSources.count { list.append( - datasources[section] + dataSources[section] .reload(response, relays: relays) - .map { LocationCellViewModel(group: SelectLocationGroup.allCases[section], location: $0) } + .map { LocationCellViewModel(group: SelectLocationSection.allCases[section], location: $0) } ) } filterRelays(by: currentSearchString) @@ -63,27 +63,27 @@ final class LocationDataSource: UITableViewDiffableDataSource<SelectLocationGrou func indexPathForSelectedRelay() -> IndexPath? { selectedRelayLocation.flatMap { - return indexPath(for: $0) + indexPath(for: $0) } } func filterRelays(by searchString: String) { currentSearchString = searchString - var list: [[LocationCellViewModel]] = [] - for section in 0 ..< SelectLocationGroup.allCases.count { - list.append( - datasources[section] - .search(by: searchString) - .map { LocationCellViewModel(group: SelectLocationGroup.allCases[section], location: $0) } - ) + + let list = SelectLocationSection.allCases.enumerated().map { section, group in + dataSources[section] + .search(by: searchString) + .map { LocationCellViewModel(group: group, location: $0) } } + updateDataSnapshot(with: list, reloadExisting: !searchString.isEmpty) + if searchString.isEmpty { - self.setSelectedRelayLocation(self.selectedRelayLocation, animated: false, completion: { + setSelectedRelayLocation(selectedRelayLocation, animated: false, completion: { self.scrollToSelectedRelay() }) } else { - self.scrollToTop(animated: false) + scrollToTop(animated: false) } } @@ -93,23 +93,23 @@ final class LocationDataSource: UITableViewDiffableDataSource<SelectLocationGrou animated: Bool = false, completion: (() -> Void)? = nil ) { - var snapshot = NSDiffableDataSourceSnapshot<SelectLocationGroup, LocationCellViewModel>() + var snapshot = NSDiffableDataSourceSnapshot<SelectLocationSection, LocationCellViewModel>() - let sections = Array(SelectLocationGroup.allCases) + let sections = SelectLocationSection.allCases snapshot.appendSections(sections) for (index, section) in sections.enumerated() { snapshot.appendItems(list[index], toSection: section) } if reloadExisting { - snapshot.reloadSections(SelectLocationGroup.allCases) + snapshot.reloadSections(SelectLocationSection.allCases) } apply(snapshot, animatingDifferences: animated, completion: completion) } private func registerClasses() { - SelectLocationGroup.allCases.forEach { + SelectLocationSection.allCases.forEach { tableView.register( $0.cell.reusableViewClass, forCellReuseIdentifier: $0.cell.reuseIdentifier @@ -117,66 +117,64 @@ final class LocationDataSource: UITableViewDiffableDataSource<SelectLocationGrou } } - private func item(for indexPath: IndexPath) -> LocationCellViewModel? { - itemIdentifier(for: indexPath) - } - private func setSelectedRelayLocation( _ relayLocation: LocationCellViewModel?, animated: Bool, completion: (() -> Void)? = nil ) { selectedRelayLocation = relayLocation - selectedRelayLocation - .flatMap { item in - let group = item.group - var locationList = snapshot().itemIdentifiers(inSection: group) - guard !locationList.contains(item) else { - completion?() - return - } - let selectedLocationTree = item.location.ascendants + [item.location] + guard let selectedRelayLocation else { return } - guard let first = selectedLocationTree.first else { return } - let topLocation = LocationCellViewModel(group: group, location: first) + let group = selectedRelayLocation.group + var locationList = snapshot().itemIdentifiers(inSection: group) + guard !locationList.contains(selectedRelayLocation) else { + completion?() + return + } + let selectedLocationTree = selectedRelayLocation.location.ancestors + [selectedRelayLocation.location] - guard let indexPath = indexPath(for: topLocation), - let topNode = node(for: topLocation) else { - return - } + guard let first = selectedLocationTree.first else { return } + let topLocation = LocationCellViewModel(group: group, location: first) - selectedLocationTree.forEach { location in - node(for: LocationCellViewModel(group: group, location: location))?.showsChildren = true - } + guard let indexPath = indexPath(for: topLocation), + let topNode = node(for: topLocation) else { + return + } - locationList.addLocations( - topNode.flatRelayLocationList().map { LocationCellViewModel(group: group, location: $0) }, - at: indexPath.row + 1 - ) - var list: [[LocationCellViewModel]] = Array(repeating: [], count: datasources.count) - for index in 0 ..< list.count { - list[index] = (index == indexPath.section) - ? locationList - : snapshot().itemIdentifiers(inSection: SelectLocationGroup.allCases[index]) - } + selectedLocationTree.forEach { location in + node(for: LocationCellViewModel(group: group, location: location))?.showsChildren = true + } - updateDataSnapshot( - with: list, - reloadExisting: true, - animated: animated, - completion: completion - ) - } + locationList.addLocations( + topNode.flatRelayLocationList().map { LocationCellViewModel(group: group, location: $0) }, + at: indexPath.row + 1 + ) + + var list: [[LocationCellViewModel]] = Array(repeating: [], count: dataSources.count) + for index in 0 ..< list.count { + list[index] = (index == indexPath.section) + ? locationList + : snapshot().itemIdentifiers(inSection: SelectLocationSection.allCases[index]) + } + + updateDataSnapshot( + with: list, + reloadExisting: true, + animated: animated, + completion: completion + ) } } extension LocationDataSource: UITableViewDelegate { func tableView(_ tableView: UITableView, shouldHighlightRowAt indexPath: IndexPath) -> Bool { - item(for: indexPath).flatMap { node(for: $0) }?.isActive ?? false + guard let item = itemIdentifier(for: indexPath) else { return false } + return node(for: item)?.isActive ?? false } func tableView(_ tableView: UITableView, indentationLevelForRowAt indexPath: IndexPath) -> Int { - item(for: indexPath).flatMap { node(for: $0) }?.indentationLevel ?? 0 + guard let item = itemIdentifier(for: indexPath) else { return 0 } + return node(for: item)?.indentationLevel ?? 0 } func tableView( @@ -184,18 +182,20 @@ extension LocationDataSource: UITableViewDelegate { willDisplay cell: UITableViewCell, forRowAt indexPath: IndexPath ) { - if let item = item(for: indexPath), + if let item = itemIdentifier(for: indexPath), item == selectedRelayLocation { cell.setSelected(true, animated: false) } } func tableView(_ tableView: UITableView, didSelectRowAt indexPath: IndexPath) { - item(for: indexPath) + itemIdentifier(for: indexPath) .flatMap { item in guard item.location != selectedRelayLocation?.location else { return } didSelectRelayLocation?(item.location) + setSelectedRelayLocation(item, animated: false) + indexPathForSelectedRelay().flatMap { let cell = tableView.cellForRow(at: $0) cell?.setSelected(false, animated: false) @@ -205,43 +205,48 @@ extension LocationDataSource: UITableViewDelegate { } extension LocationDataSource: LocationCellEventHandler { - func collapseCell(for item: LocationCellViewModel) { + func toggleCell(for item: LocationCellViewModel) { indexPath(for: item).flatMap { indexPath in - guard let node = self.node(for: item), - let cell = tableView.cellForRow(at: indexPath) else { return } + guard let node = node(for: item), let cell = tableView.cellForRow(at: indexPath) else { return } + let isExpanded = node.showsChildren - let group = SelectLocationGroup.allCases[indexPath.section] + let group = SelectLocationSection.allCases[indexPath.section] + node.showsChildren = !isExpanded locationCellFactory.configureCell( cell, item: LocationCellViewModel(group: group, location: node.location), indexPath: indexPath ) + var locationList = snapshot().itemIdentifiers(inSection: group) let locationsToEdit = node.flatRelayLocationList().map { LocationCellViewModel(group: group, location: $0) } + if !isExpanded { locationList.addLocations(locationsToEdit, at: indexPath.row + 1) } else { locationsToEdit.forEach { self.node(for: $0)?.showsChildren = false } locationList.removeLocations(locationsToEdit) } - var list: [[LocationCellViewModel]] = Array(repeating: [], count: datasources.count) + + var list: [[LocationCellViewModel]] = Array(repeating: [], count: dataSources.count) for index in 0 ..< list.count { list[index] = (index == indexPath.section) ? locationList - : snapshot().itemIdentifiers(inSection: SelectLocationGroup.allCases[index]) + : snapshot().itemIdentifiers(inSection: SelectLocationSection.allCases[index]) } - self.updateDataSnapshot(with: list, completion: { + + updateDataSnapshot(with: list, completion: { self.scroll(to: item, animated: true) }) } } func node(for item: LocationCellViewModel) -> SelectLocationNode? { - guard let sectionIndex = SelectLocationGroup.allCases.firstIndex(of: item.group) else { + guard let sectionIndex = SelectLocationSection.allCases.firstIndex(of: item.group) else { return nil } - return datasources[sectionIndex].nodeByLocation[item.location] + return dataSources[sectionIndex].nodeByLocation[item.location] } } @@ -256,7 +261,7 @@ extension LocationDataSource { } else { node.children.last.flatMap { last in if let lastInsertedIndexPath = self.indexPath(for: LocationCellViewModel( - group: SelectLocationGroup.allCases[indexPath.section], + group: SelectLocationSection.allCases[indexPath.section], location: last.location )), let lastVisibleIndexPath = visibleIndexPaths.last, diff --git a/ios/MullvadVPN/View controllers/SelectLocation/LocationDataSourceProtocol.swift b/ios/MullvadVPN/View controllers/SelectLocation/LocationDataSourceProtocol.swift index f00cdf3408..6511f4bd44 100644 --- a/ios/MullvadVPN/View controllers/SelectLocation/LocationDataSourceProtocol.swift +++ b/ios/MullvadVPN/View controllers/SelectLocation/LocationDataSourceProtocol.swift @@ -29,18 +29,18 @@ extension LocationDataSourceProtocol { func createNode( root: SelectLocationNode, - ascendantOrSelf: RelayLocation, + ancestorOrSelf: RelayLocation, serverLocation: REST.ServerLocation, relay: REST.ServerRelay, wasShowingChildren: Bool ) -> SelectLocationNode { let node: SelectLocationNode - switch ascendantOrSelf { + switch ancestorOrSelf { case .country: node = SelectLocationNode( nodeType: .country, - location: ascendantOrSelf, + location: ancestorOrSelf, displayName: serverLocation.country, showsChildren: wasShowingChildren ) @@ -48,7 +48,7 @@ extension LocationDataSourceProtocol { case let .city(countryCode, _): node = SelectLocationNode( nodeType: .city, - location: ascendantOrSelf, + location: ancestorOrSelf, displayName: serverLocation.city, showsChildren: wasShowingChildren ) @@ -57,7 +57,7 @@ extension LocationDataSourceProtocol { case let .hostname(countryCode, cityCode, _): node = SelectLocationNode( nodeType: .relay, - location: ascendantOrSelf, + location: ancestorOrSelf, displayName: relay.hostname, isActive: relay.active ) diff --git a/ios/MullvadVPN/View controllers/SelectLocation/SelectLocationGroup.swift b/ios/MullvadVPN/View controllers/SelectLocation/SelectLocationSection.swift index 1d5b66dcf2..2e0984c809 100644 --- a/ios/MullvadVPN/View controllers/SelectLocation/SelectLocationGroup.swift +++ b/ios/MullvadVPN/View controllers/SelectLocation/SelectLocationSection.swift @@ -7,7 +7,7 @@ // import Foundation -enum SelectLocationGroup: Hashable, CustomStringConvertible, CaseIterable { +enum SelectLocationSection: Hashable, CustomStringConvertible, CaseIterable { case customLists case allLocations @@ -32,7 +32,7 @@ enum SelectLocationGroup: Hashable, CustomStringConvertible, CaseIterable { Cell.locationCell } - static var allCases: [SelectLocationGroup] { + static var allCases: [SelectLocationSection] { #if DEBUG return [.customLists, .allLocations] #else @@ -41,7 +41,7 @@ enum SelectLocationGroup: Hashable, CustomStringConvertible, CaseIterable { } } -extension SelectLocationGroup { +extension SelectLocationSection { enum Cell: String, CaseIterable { case locationCell |
