Impressia/Vernissage/ViewModels/StatusViewModel.swift

175 lines
5.4 KiB
Swift
Raw Normal View History

2023-01-10 20:38:02 +01:00
//
// https://mczachurski.dev
// Copyright © 2023 Marcin Czachurski and the repository contributors.
// Licensed under the MIT License.
//
import Foundation
import MastodonKit
2023-01-26 15:10:47 +01:00
public class StatusViewModel: ObservableObject {
2023-01-10 20:38:02 +01:00
2023-01-18 18:41:42 +01:00
public let id: EntityId
2023-01-10 20:38:02 +01:00
public let content: Html
public let uri: String?
public let url: URL?
public let account: Account
2023-01-22 13:49:19 +01:00
public let inReplyToId: EntityId?
2023-01-18 18:41:42 +01:00
public let inReplyToAccount: EntityId?
2023-01-26 15:10:47 +01:00
2023-01-10 20:38:02 +01:00
public let createdAt: String
public let reblogsCount: Int
public let favouritesCount: Int
public let repliesCount: Int
public let reblogged: Bool
public let favourited: Bool
public let sensitive: Bool
public let bookmarked: Bool
public let pinned: Bool
public let muted: Bool
public let spoilerText: String?
public let visibility: Status.Visibility
2023-01-22 13:49:19 +01:00
public let card: PreviewCard?
2023-01-10 20:38:02 +01:00
public let mentions: [Mention]
public let tags: [Tag]
2023-01-22 13:49:19 +01:00
public let application: BaseApplication?
2023-01-10 21:11:04 +01:00
public let place: Place?
2023-01-10 20:38:02 +01:00
2023-01-26 15:10:47 +01:00
public let reblogStatus: Status?
@Published public var mediaAttachments: [AttachmentViewModel]
2023-01-10 20:38:02 +01:00
public init(
2023-01-18 18:41:42 +01:00
id: EntityId,
2023-01-10 20:38:02 +01:00
content: Html,
uri: String,
account: Account,
2023-01-22 13:49:19 +01:00
application: BaseApplication,
2023-01-10 20:38:02 +01:00
url: URL? = nil,
2023-01-22 13:49:19 +01:00
inReplyToId: EntityId? = nil,
2023-01-18 18:41:42 +01:00
inReplyToAccount: EntityId? = nil,
2023-01-10 20:38:02 +01:00
reblog: Status? = nil,
createdAt: String? = nil,
reblogsCount: Int = 0,
favouritesCount: Int = 0,
repliesCount: Int = 0,
reblogged: Bool = false,
favourited: Bool = false,
sensitive: Bool = false,
bookmarked: Bool = false,
pinned: Bool = false,
muted: Bool = false,
spoilerText: String? = nil,
visibility: Status.Visibility = Status.Visibility.pub,
mediaAttachments: [AttachmentViewModel] = [],
2023-01-22 13:49:19 +01:00
card: PreviewCard? = nil,
2023-01-10 20:38:02 +01:00
mentions: [Mention] = [],
tags: [Tag] = [],
2023-01-10 21:11:04 +01:00
place: Place? = nil
2023-01-10 20:38:02 +01:00
) {
self.id = id
self.content = content
self.uri = uri
self.url = url
self.account = account
2023-01-10 21:11:04 +01:00
self.application = application
2023-01-10 20:38:02 +01:00
self.inReplyToId = inReplyToId
self.inReplyToAccount = inReplyToAccount
self.createdAt = createdAt ?? Date().formatted(.iso8601)
self.reblogsCount = reblogsCount
self.favouritesCount = favouritesCount
self.repliesCount = repliesCount
self.reblogged = reblogged
self.favourited = favourited
self.sensitive = sensitive
self.bookmarked = bookmarked
self.pinned = pinned
self.muted = muted
self.spoilerText = spoilerText
self.visibility = visibility
self.mediaAttachments = mediaAttachments
self.card = card
self.mentions = mentions
self.tags = tags
2023-01-10 21:11:04 +01:00
self.place = place
2023-01-26 15:10:47 +01:00
self.reblogStatus = nil
2023-01-10 20:38:02 +01:00
}
init(status: Status) {
2023-01-26 15:10:47 +01:00
// If status has been rebloged we are saving orginal status here.
let orginalStatus = status.reblog ?? status
self.id = orginalStatus.id
self.content = orginalStatus.content
self.uri = orginalStatus.uri
self.url = orginalStatus.url
self.account = orginalStatus.account
self.inReplyToId = orginalStatus.inReplyToId
self.inReplyToAccount = orginalStatus.inReplyToAccount
self.createdAt = orginalStatus.createdAt
self.reblogsCount = orginalStatus.reblogsCount
self.favouritesCount = orginalStatus.favouritesCount
self.repliesCount = orginalStatus.repliesCount
self.reblogged = orginalStatus.reblogged
self.favourited = orginalStatus.favourited
self.sensitive = orginalStatus.sensitive
self.bookmarked = orginalStatus.bookmarked
self.pinned = orginalStatus.pinned
self.muted = orginalStatus.muted
self.spoilerText = orginalStatus.spoilerText
self.visibility = orginalStatus.visibility
self.card = orginalStatus.card
self.mentions = orginalStatus.mentions
self.tags = orginalStatus.tags
self.application = orginalStatus.application
self.place = orginalStatus.place
2023-01-10 20:38:02 +01:00
var mediaAttachments: [AttachmentViewModel] = []
2023-01-26 15:10:47 +01:00
for item in orginalStatus.mediaAttachments {
2023-01-10 20:38:02 +01:00
mediaAttachments.append(AttachmentViewModel(attachment: item))
}
self.mediaAttachments = mediaAttachments
2023-01-26 15:10:47 +01:00
if status.reblog != nil {
self.reblogStatus = status
} else {
self.reblogStatus = nil
}
2023-01-10 20:38:02 +01:00
}
}
public extension StatusViewModel {
func getImageWidth() -> Int32? {
2023-01-27 15:46:09 +01:00
let highestImage = self.mediaAttachments.getHighestImage()
if let width = (highestImage?.meta as? ImageMetadata)?.original?.width {
2023-01-10 20:38:02 +01:00
return Int32(width)
} else {
return nil
}
}
func getImageHeight() -> Int32? {
2023-01-27 15:46:09 +01:00
let highestImage = self.mediaAttachments.getHighestImage()
if let height = (highestImage?.meta as? ImageMetadata)?.original?.height {
2023-01-10 20:38:02 +01:00
return Int32(height)
} else {
return nil
}
}
}
public extension [Status] {
func toStatusViewModel() -> [StatusViewModel] {
2023-01-14 08:52:51 +01:00
self
.sorted(by: { lhs, rhs in
lhs.id < rhs.id
})
.map { status in
StatusViewModel(status: status)
}
2023-01-10 20:38:02 +01:00
}
}