Refactoring

This commit is contained in:
Justin Mazzocchi 2020-09-09 15:48:56 -07:00
parent 4c1f0e2452
commit 182ecb5b91
No known key found for this signature in database
GPG key ID: E223E6937AAFB01C
8 changed files with 58 additions and 55 deletions

View file

@ -47,7 +47,7 @@ public extension RootViewModel {
}
public extension Identification {
static let preview = RootViewModel.preview.identification!
static let preview = RootViewModel.preview.navigationViewModel!.identification
}
// swiftlint:enable force_try

View file

@ -5,7 +5,7 @@ import Foundation
import ServiceLayer
public final class Identification: ObservableObject {
@Published private(set) var identity: Identity
@Published private(set) public var identity: Identity
let service: IdentityService
init(identity: Identity, observation: AnyPublisher<Identity, Never>, service: IdentityService) {

View file

@ -5,24 +5,7 @@ import Foundation
import ServiceLayer
public final class RootViewModel: ObservableObject {
@Published public private(set) var identification: Identification? {
didSet {
guard let identification = identification else { return }
identification.service.updateLastUse()
.sink { _ in } receiveValue: { _ in }
.store(in: &cancellables)
userNotificationService.isAuthorized()
.filter { $0 }
.zip(registerForRemoteNotifications())
.filter { identification.identity.lastRegisteredDeviceToken != $1 }
.map { ($1, identification.identity.pushSubscriptionAlerts) }
.flatMap(identification.service.createPushSubscription(deviceToken:alerts:))
.sink { _ in } receiveValue: { _ in }
.store(in: &cancellables)
}
}
@Published public private(set) var navigationViewModel: TabNavigationViewModel?
@Published private var mostRecentlyUsedIdentityID: UUID?
private let environment: AppEnvironment
@ -74,10 +57,12 @@ public extension RootViewModel {
private extension RootViewModel {
func identitySelected(id: UUID?, immediate: Bool) {
navigationViewModel?.presentingSecondaryNavigation = false
guard
let id = id,
let identityService = try? allIdentitiesService.identityService(id: id) else {
identification = nil
navigationViewModel = nil
return
}
@ -93,13 +78,30 @@ private extension RootViewModel {
.share()
observation
.filter { [weak self] in $0.id != self?.identification?.identity.id }
.map {
Identification(
.filter { [weak self] in $0.id != self?.navigationViewModel?.identification.identity.id }
.map { [weak self] in
let identification = Identification(
identity: $0,
observation: observation.eraseToAnyPublisher(),
service: identityService)
if let self = self {
identification.service.updateLastUse()
.sink { _ in } receiveValue: { _ in }
.store(in: &self.cancellables)
self.userNotificationService.isAuthorized()
.filter { $0 }
.zip(self.registerForRemoteNotifications())
.filter { identification.identity.lastRegisteredDeviceToken != $1 }
.map { ($1, identification.identity.pushSubscriptionAlerts) }
.flatMap(identification.service.createPushSubscription(deviceToken:alerts:))
.sink { _ in } receiveValue: { _ in }
.store(in: &self.cancellables)
}
return TabNavigationViewModel(identification: identification)
}
.assign(to: &$identification)
.assign(to: &$navigationViewModel)
}
}

View file

@ -6,7 +6,7 @@ import Mastodon
import ServiceLayer
public final class TabNavigationViewModel: ObservableObject {
@Published public private(set) var identity: Identity
public let identification: Identification
@Published public private(set) var recentIdentities = [Identity]()
@Published public var timeline: Timeline
@Published public private(set) var timelinesAndLists: [Timeline]
@ -14,18 +14,19 @@ public final class TabNavigationViewModel: ObservableObject {
@Published public var alertItem: AlertItem?
public var selectedTab: Tab? = .timelines
private let identification: Identification
private var cancellables = Set<AnyCancellable>()
public init(identification: Identification) {
self.identification = identification
identity = identification.identity
timeline = identification.service.isAuthorized ? .home : .local
timelinesAndLists = identification.service.isAuthorized
? Timeline.authenticatedDefaults
: Timeline.unauthenticatedDefaults
identification.$identity.dropFirst().assign(to: &$identity)
identification.$identity
.sink { [weak self] _ in self?.objectWillChange.send() }
.store(in: &cancellables)
identification.service.recentIdentitiesObservation()
.assignErrorsToAlertItem(to: \.alertItem, on: self)
.assign(to: &$recentIdentities)
@ -51,9 +52,9 @@ public extension TabNavigationViewModel {
var timelineSubtitle: String {
switch timeline {
case .home, .list:
return identity.handle
return identification.identity.handle
case .local, .federated, .tag:
return identity.instance?.uri ?? ""
return identification.identity.instance?.uri ?? ""
}
}
@ -72,7 +73,7 @@ public extension TabNavigationViewModel {
.sink { _ in }
.store(in: &cancellables)
if identity.preferences.useServerPostingReadingPreferences {
if identification.identity.preferences.useServerPostingReadingPreferences {
identification.service.refreshServerPreferences()
.assignErrorsToAlertItem(to: \.alertItem, on: self)
.sink { _ in }

View file

@ -5,7 +5,7 @@ import ViewModels
struct ListsView: View {
@StateObject var viewModel: ListsViewModel
@EnvironmentObject var tabNavigationViewModel: TabNavigationViewModel
@EnvironmentObject var rootViewModel: RootViewModel
@State private var newListTitle = ""
var body: some View {
@ -28,8 +28,8 @@ struct ListsView: View {
Section {
ForEach(viewModel.lists) { list in
Button(list.title) {
tabNavigationViewModel.timeline = .list(list)
tabNavigationViewModel.presentingSecondaryNavigation = false
rootViewModel.navigationViewModel?.timeline = .list(list)
rootViewModel.navigationViewModel?.presentingSecondaryNavigation = false
}
}
.onDelete {

View file

@ -7,11 +7,9 @@ struct RootView: View {
@StateObject var viewModel: RootViewModel
var body: some View {
if let identification = viewModel.identification {
TabNavigationView()
.id(UUID())
.environmentObject(identification)
.environmentObject(TabNavigationViewModel(identification: identification))
if let navigationViewModel = viewModel.navigationViewModel {
TabNavigationView(viewModel: navigationViewModel)
.id(navigationViewModel.identification.identity.id)
.environmentObject(viewModel)
.transition(.opacity)
} else {

View file

@ -5,8 +5,9 @@ import SwiftUI
import ViewModels
struct SecondaryNavigationView: View {
@ObservedObject var viewModel: TabNavigationViewModel
@EnvironmentObject var identification: Identification
@EnvironmentObject var tabNavigationViewModel: TabNavigationViewModel
@EnvironmentObject var rootViewModel: RootViewModel
@Environment(\.displayScale) var displayScale: CGFloat
var body: some View {
@ -17,25 +18,25 @@ struct SecondaryNavigationView: View {
destination: IdentitiesView(viewModel: .init(identification: identification)),
label: {
HStack {
KFImage(tabNavigationViewModel.identity.image,
KFImage(identification.identity.image,
options: .downsampled(dimension: 50, scaleFactor: displayScale))
VStack(alignment: .leading) {
if tabNavigationViewModel.identity.authenticated {
if let account = tabNavigationViewModel.identity.account {
if identification.identity.authenticated {
if let account = identification.identity.account {
CustomEmojiText(
text: account.displayName,
emoji: account.emojis,
textStyle: .headline)
}
Text(tabNavigationViewModel.identity.handle)
Text(identification.identity.handle)
.font(.subheadline)
.foregroundColor(.secondary)
.lineLimit(1)
.minimumScaleFactor(0.5)
} else {
Text(tabNavigationViewModel.identity.handle)
Text(identification.identity.handle)
.font(.headline)
if let instance = tabNavigationViewModel.identity.instance {
if let instance = identification.identity.instance {
Text(instance.uri)
.font(.subheadline)
.foregroundColor(.secondary)
@ -68,7 +69,7 @@ struct SecondaryNavigationView: View {
.toolbar {
ToolbarItem(placement: .cancellationAction) {
Button {
tabNavigationViewModel.presentingSecondaryNavigation = false
viewModel.presentingSecondaryNavigation = false
} label: {
Image(systemName: "xmark.circle.fill")
}
@ -84,9 +85,9 @@ import PreviewViewModels
struct SecondaryNavigationView_Previews: PreviewProvider {
static var previews: some View {
SecondaryNavigationView()
SecondaryNavigationView(viewModel: TabNavigationViewModel(identification: .preview))
.environmentObject(Identification.preview)
.environmentObject(TabNavigationViewModel(identification: .preview))
.environmentObject(RootViewModel.preview)
}
}
#endif

View file

@ -6,7 +6,7 @@ import SwiftUI
import ViewModels
struct TabNavigationView: View {
@EnvironmentObject var viewModel: TabNavigationViewModel
@ObservedObject var viewModel: TabNavigationViewModel
@EnvironmentObject var rootViewModel: RootViewModel
@Environment(\.displayScale) var displayScale: CGFloat
@ -24,8 +24,10 @@ struct TabNavigationView: View {
.tag(tab)
}
}
.environmentObject(viewModel.identification)
.sheet(isPresented: $viewModel.presentingSecondaryNavigation) {
SecondaryNavigationView()
SecondaryNavigationView(viewModel: viewModel)
.environmentObject(viewModel.identification)
.environmentObject(viewModel)
.environmentObject(rootViewModel)
}
@ -81,7 +83,7 @@ private extension TabNavigationView {
Button {
viewModel.presentingSecondaryNavigation.toggle()
} label: {
KFImage(viewModel.identity.image,
KFImage(viewModel.identification.identity.image,
options: .downsampled(dimension: 28, scaleFactor: displayScale))
.placeholder { Image(systemName: "gear") }
.renderingMode(.original)
@ -156,9 +158,8 @@ import PreviewViewModels
struct TabNavigation_Previews: PreviewProvider {
static var previews: some View {
TabNavigationView()
TabNavigationView(viewModel: TabNavigationViewModel(identification: .preview))
.environmentObject(Identification.preview)
.environmentObject(TabNavigationViewModel(identification: .preview))
.environmentObject(RootViewModel.preview)
}
}