Show inline actions for remote local timeline + fetch remote status

This commit is contained in:
Thomas Ricouard 2023-02-13 06:48:29 +01:00
parent ef37db496c
commit 9867faa6de
3 changed files with 42 additions and 15 deletions

View file

@ -76,7 +76,7 @@ struct StatusActionsView: View {
HStack(spacing: 2) { HStack(spacing: 2) {
Image(systemName: action.iconName(viewModel: viewModel)) Image(systemName: action.iconName(viewModel: viewModel))
.foregroundColor(action.tintColor(viewModel: viewModel, theme: theme)) .foregroundColor(action.tintColor(viewModel: viewModel, theme: theme))
if let count = action.count(viewModel: viewModel, theme: theme) { if let count = action.count(viewModel: viewModel, theme: theme), !viewModel.isRemote {
Text("\(count)") Text("\(count)")
.font(.scaledFootnote) .font(.scaledFootnote)
} }
@ -97,10 +97,15 @@ struct StatusActionsView: View {
private func handleAction(action: Actions) { private func handleAction(action: Actions) {
Task { Task {
if viewModel.isRemote, viewModel.localStatusId == nil || viewModel.localStatus == nil {
guard await viewModel.fetchRemoteStatus() else {
return
}
}
HapticManager.shared.fireHaptic(of: .notification(.success)) HapticManager.shared.fireHaptic(of: .notification(.success))
switch action { switch action {
case .respond: case .respond:
routerPath.presentedSheet = .replyToStatusEditor(status: viewModel.status) routerPath.presentedSheet = .replyToStatusEditor(status: viewModel.localStatus ?? viewModel.status)
case .favorite: case .favorite:
if viewModel.isFavorited { if viewModel.isFavorited {
await viewModel.unFavorite() await viewModel.unFavorite()

View file

@ -53,7 +53,7 @@ public struct StatusRowView: View {
replyView replyView
} }
statusView statusView
if viewModel.showActions && !viewModel.isRemote, theme.statusActionsDisplay != .none { if viewModel.showActions, theme.statusActionsDisplay != .none {
StatusActionsView(viewModel: viewModel) StatusActionsView(viewModel: viewModel)
.padding(.top, 8) .padding(.top, 8)
.tint(viewModel.isFocused ? theme.tintColor : .gray) .tint(viewModel.isFocused ? theme.tintColor : .gray)
@ -465,20 +465,20 @@ public struct StatusRowView: View {
@ViewBuilder @ViewBuilder
private var trailingSwipeActions: some View { private var trailingSwipeActions: some View {
if preferences.swipeActionsStatusTrailingRight != StatusAction.none { if preferences.swipeActionsStatusTrailingRight != StatusAction.none, !viewModel.isRemote {
makeSwipeButton(action: preferences.swipeActionsStatusTrailingRight) makeSwipeButton(action: preferences.swipeActionsStatusTrailingRight)
} }
if preferences.swipeActionsStatusTrailingLeft != StatusAction.none { if preferences.swipeActionsStatusTrailingLeft != StatusAction.none, !viewModel.isRemote {
makeSwipeButton(action: preferences.swipeActionsStatusTrailingLeft) makeSwipeButton(action: preferences.swipeActionsStatusTrailingLeft)
} }
} }
@ViewBuilder @ViewBuilder
private var leadingSwipeActions: some View { private var leadingSwipeActions: some View {
if preferences.swipeActionsStatusLeadingLeft != StatusAction.none { if preferences.swipeActionsStatusLeadingLeft != StatusAction.none, !viewModel.isRemote {
makeSwipeButton(action: preferences.swipeActionsStatusLeadingLeft) makeSwipeButton(action: preferences.swipeActionsStatusLeadingLeft)
} }
if preferences.swipeActionsStatusLeadingRight != StatusAction.none { if preferences.swipeActionsStatusLeadingRight != StatusAction.none, !viewModel.isRemote {
makeSwipeButton(action: preferences.swipeActionsStatusLeadingRight) makeSwipeButton(action: preferences.swipeActionsStatusLeadingRight)
} }
} }

View file

@ -13,7 +13,7 @@ public class StatusRowViewModel: ObservableObject {
let isFocused: Bool let isFocused: Bool
let isRemote: Bool let isRemote: Bool
let showActions: Bool let showActions: Bool
@Published var favoritesCount: Int @Published var favoritesCount: Int
@Published var isFavorited: Bool @Published var isFavorited: Bool
@Published var isReblogged: Bool @Published var isReblogged: Bool
@ -25,7 +25,6 @@ public class StatusRowViewModel: ObservableObject {
@Published var displaySpoiler: Bool = false @Published var displaySpoiler: Bool = false
@Published var isEmbedLoading: Bool = false @Published var isEmbedLoading: Bool = false
@Published var isFiltered: Bool = false @Published var isFiltered: Bool = false
@Published var isLoadingRemoteContent: Bool = false
@Published var translation: StatusTranslation? @Published var translation: StatusTranslation?
@Published var isLoadingTranslation: Bool = false @Published var isLoadingTranslation: Bool = false
@ -33,6 +32,10 @@ public class StatusRowViewModel: ObservableObject {
@Published var favoriters: [Account] = [] @Published var favoriters: [Account] = []
@Published var rebloggers: [Account] = [] @Published var rebloggers: [Account] = []
@Published var isLoadingRemoteContent: Bool = false
@Published var localStatusId: String?
@Published var localStatus: Status?
private let theme = Theme.shared private let theme = Theme.shared
@ -168,7 +171,7 @@ public class StatusRowViewModel: ObservableObject {
isFavorited = true isFavorited = true
favoritesCount += 1 favoritesCount += 1
do { do {
let status: Status = try await client.post(endpoint: Statuses.favorite(id: status.reblog?.id ?? status.id)) let status: Status = try await client.post(endpoint: Statuses.favorite(id: localStatusId ?? status.reblog?.id ?? status.id))
updateFromStatus(status: status) updateFromStatus(status: status)
} catch { } catch {
isFavorited = false isFavorited = false
@ -181,7 +184,7 @@ public class StatusRowViewModel: ObservableObject {
isFavorited = false isFavorited = false
favoritesCount -= 1 favoritesCount -= 1
do { do {
let status: Status = try await client.post(endpoint: Statuses.unfavorite(id: status.reblog?.id ?? status.id)) let status: Status = try await client.post(endpoint: Statuses.unfavorite(id: localStatusId ?? status.reblog?.id ?? status.id))
updateFromStatus(status: status) updateFromStatus(status: status)
} catch { } catch {
isFavorited = true isFavorited = true
@ -194,7 +197,7 @@ public class StatusRowViewModel: ObservableObject {
isReblogged = true isReblogged = true
reblogsCount += 1 reblogsCount += 1
do { do {
let status: Status = try await client.post(endpoint: Statuses.reblog(id: status.reblog?.id ?? status.id)) let status: Status = try await client.post(endpoint: Statuses.reblog(id: localStatusId ?? status.reblog?.id ?? status.id))
updateFromStatus(status: status) updateFromStatus(status: status)
} catch { } catch {
isReblogged = false isReblogged = false
@ -207,7 +210,7 @@ public class StatusRowViewModel: ObservableObject {
isReblogged = false isReblogged = false
reblogsCount -= 1 reblogsCount -= 1
do { do {
let status: Status = try await client.post(endpoint: Statuses.unreblog(id: status.reblog?.id ?? status.id)) let status: Status = try await client.post(endpoint: Statuses.unreblog(id: localStatusId ?? status.reblog?.id ?? status.id))
updateFromStatus(status: status) updateFromStatus(status: status)
} catch { } catch {
isReblogged = true isReblogged = true
@ -241,7 +244,7 @@ public class StatusRowViewModel: ObservableObject {
guard let client, client.isAuth else { return } guard let client, client.isAuth else { return }
isBookmarked = true isBookmarked = true
do { do {
let status: Status = try await client.post(endpoint: Statuses.bookmark(id: status.reblog?.id ?? status.id)) let status: Status = try await client.post(endpoint: Statuses.bookmark(id: localStatusId ?? status.reblog?.id ?? status.id))
updateFromStatus(status: status) updateFromStatus(status: status)
} catch { } catch {
isBookmarked = false isBookmarked = false
@ -252,7 +255,7 @@ public class StatusRowViewModel: ObservableObject {
guard let client, client.isAuth else { return } guard let client, client.isAuth else { return }
isBookmarked = false isBookmarked = false
do { do {
let status: Status = try await client.post(endpoint: Statuses.unbookmark(id: status.reblog?.id ?? status.id)) let status: Status = try await client.post(endpoint: Statuses.unbookmark(id: localStatusId ?? status.reblog?.id ?? status.id))
updateFromStatus(status: status) updateFromStatus(status: status)
} catch { } catch {
isBookmarked = true isBookmarked = true
@ -324,4 +327,23 @@ public class StatusRowViewModel: ObservableObject {
} }
} }
} }
func fetchRemoteStatus() async -> Bool {
guard isRemote, let client, let remoteStatusURL = URL(string: status.reblog?.url ?? status.url ?? "") else { return false }
isLoadingRemoteContent = true
let results: SearchResults? = try? await client.get(endpoint: Search.search(query: remoteStatusURL.absoluteString,
type: "statuses",
offset: nil,
following: nil),
forceVersion: .v2)
if let status = results?.statuses.first {
self.localStatusId = status.id
self.localStatus = status
isLoadingRemoteContent = false
return true
} else {
isLoadingRemoteContent = false
return false
}
}
} }