IceCubesApp/Packages/Status/Sources/Status/Row/Subviews/StatusRowHeaderView.swift

118 lines
3.6 KiB
Swift
Raw Normal View History

import DesignSystem
2023-02-21 06:23:42 +00:00
import Env
import Models
2023-02-18 06:26:48 +00:00
import SwiftUI
struct StatusRowHeaderView: View {
2023-02-19 14:29:07 +00:00
@Environment(\.isInCaptureMode) private var isInCaptureMode: Bool
@EnvironmentObject private var theme: Theme
2023-02-18 06:26:48 +00:00
let viewModel: StatusRowViewModel
2023-02-18 06:26:48 +00:00
var body: some View {
HStack(alignment: .center) {
Button {
2023-03-02 05:56:25 +00:00
viewModel.navigateToAccountDetail(account: viewModel.finalStatus.account)
} label: {
2023-03-02 05:56:25 +00:00
accountView
}
.buttonStyle(.plain)
Spacer()
2023-02-19 14:29:07 +00:00
if !isInCaptureMode {
threadIcon
contextMenuButton
}
}
.accessibilityElement()
2023-03-02 19:15:07 +00:00
.accessibilityLabel(Text("\(viewModel.finalStatus.account.safeDisplayName)"))
}
2023-02-18 06:26:48 +00:00
@ViewBuilder
2023-03-02 05:56:25 +00:00
private var accountView: some View {
HStack(alignment: .center) {
if theme.avatarPosition == .top {
2023-03-02 05:56:25 +00:00
AvatarView(url: viewModel.finalStatus.account.avatar, size: .status)
}
2023-02-19 18:51:37 +00:00
VStack(alignment: .leading, spacing: 2) {
HStack(alignment: .firstTextBaseline, spacing: 2) {
Group {
2023-03-02 05:56:25 +00:00
EmojiTextApp(.init(stringValue: viewModel.finalStatus.account.safeDisplayName),
emojis: viewModel.finalStatus.account.emojis)
.font(.scaledSubheadline)
.foregroundColor(theme.labelColor)
.emojiSize(Font.scaledSubheadlineFont.emojiSize)
.emojiBaselineOffset(Font.scaledSubheadlineFont.emojiBaselineOffset)
.fontWeight(.semibold)
.lineLimit(1)
accountBadgeView
.font(.footnote)
}
.layoutPriority(1)
if theme.avatarPosition == .leading {
dateView
2023-02-19 18:57:17 +00:00
.font(.scaledFootnote)
.foregroundColor(.gray)
.lineLimit(1)
} else {
2023-03-02 05:56:25 +00:00
Text("@\(theme.displayFullUsername ? viewModel.finalStatus.account.acct : viewModel.finalStatus.account.username)")
2023-02-19 18:57:17 +00:00
.font(.scaledFootnote)
.foregroundColor(.gray)
.lineLimit(1)
}
}
if theme.avatarPosition == .top {
2023-02-19 18:57:17 +00:00
dateView
2023-02-21 06:23:42 +00:00
.font(.scaledFootnote)
.foregroundColor(.gray)
.lineLimit(1)
} else if theme.displayFullUsername, theme.avatarPosition == .leading {
2023-03-02 05:56:25 +00:00
Text("@\(viewModel.finalStatus.account.acct)")
.font(.scaledFootnote)
.foregroundColor(.gray)
.lineLimit(1)
.offset(y: 1)
}
}
}
}
2023-02-26 05:45:57 +00:00
private var accountBadgeView: Text {
2023-02-24 16:16:39 +00:00
if (viewModel.status.reblogAsAsStatus ?? viewModel.status).account.bot {
2023-02-26 16:33:16 +00:00
return Text(Image(systemName: "poweroutlet.type.b.fill")) + Text(" ")
2023-02-24 16:16:39 +00:00
} else if (viewModel.status.reblogAsAsStatus ?? viewModel.status).account.locked {
return Text(Image(systemName: "lock.fill")) + Text(" ")
}
return Text("")
}
2023-02-21 06:23:42 +00:00
private var dateView: Text {
2023-03-02 05:56:25 +00:00
Text(viewModel.finalStatus.createdAt.relativeFormatted) +
2023-02-26 05:45:57 +00:00
Text("") +
2023-03-03 06:12:02 +00:00
Text(Image(systemName: viewModel.finalStatus.visibility.iconName))
}
2023-02-18 06:26:48 +00:00
@ViewBuilder
private var threadIcon: some View {
if viewModel.isThread {
Image(systemName: "bubble.left.and.bubble.right")
.resizable()
.aspectRatio(contentMode: .fit)
.frame(width: 15)
.foregroundColor(.gray)
}
}
2023-02-18 06:26:48 +00:00
private var contextMenuButton: some View {
Menu {
StatusRowContextMenu(viewModel: viewModel)
} label: {
Image(systemName: "ellipsis")
.frame(width: 20, height: 20)
}
.menuStyle(.borderlessButton)
.foregroundColor(.gray)
.contentShape(Rectangle())
.accessibilityHidden(true)
}
}