Kurdtvs-Live-Kurdish-TV-Kur.../Mastodon/Diffiable/Notification/NotificationSection.swift

303 lines
14 KiB
Swift

//
// NotificationSection.swift
// Mastodon
//
// Created by sxiaojian on 2021/4/13.
//
import Combine
import CoreData
import CoreDataStack
import Foundation
import MastodonSDK
import UIKit
import MetaTextKit
import MastodonMeta
import MastodonAsset
import MastodonLocalization
enum NotificationSection: Equatable, Hashable {
case main
}
extension NotificationSection {
struct Configuration {
weak var notificationTableViewCellDelegate: NotificationTableViewCellDelegate?
}
static func diffableDataSource(
tableView: UITableView,
context: AppContext,
configuration: Configuration
) -> UITableViewDiffableDataSource<NotificationSection, NotificationItem> {
tableView.register(NotificationTableViewCell.self, forCellReuseIdentifier: String(describing: NotificationTableViewCell.self))
tableView.register(TimelineBottomLoaderTableViewCell.self, forCellReuseIdentifier: String(describing: TimelineBottomLoaderTableViewCell.self))
return UITableViewDiffableDataSource(tableView: tableView) { tableView, indexPath, item -> UITableViewCell? in
switch item {
case .feed(let record):
let cell = tableView.dequeueReusableCell(withIdentifier: String(describing: NotificationTableViewCell.self), for: indexPath) as! NotificationTableViewCell
context.managedObjectContext.performAndWait {
guard let feed = record.object(in: context.managedObjectContext) else { return }
configure(
context: context,
tableView: tableView,
cell: cell,
viewModel: NotificationTableViewCell.ViewModel(value: .feed(feed)),
configuration: configuration
)
}
return cell
case .feedLoader(let record):
return UITableViewCell()
case .bottomLoader:
let cell = tableView.dequeueReusableCell(withIdentifier: String(describing: TimelineBottomLoaderTableViewCell.self), for: indexPath) as! TimelineBottomLoaderTableViewCell
cell.activityIndicatorView.startAnimating()
return cell
}
// switch notificationItem {
// case .notification(let objectID, let attribute):
// guard let notification = try? managedObjectContext.existingObject(with: objectID) as? MastodonNotification,
// !notification.isDeleted
// else { return UITableViewCell() }
//
// let cell = tableView.dequeueReusableCell(withIdentifier: String(describing: NotificationStatusTableViewCell.self), for: indexPath) as! NotificationStatusTableViewCell
// configure(
// tableView: tableView,
// cell: cell,
// notification: notification,
// dependency: dependency,
// attribute: attribute
// )
// cell.delegate = delegate
// cell.isAccessibilityElement = true
// NotificationSection.configureStatusAccessibilityLabel(cell: cell)
// return cell
//
// case .notificationStatus(objectID: let objectID, attribute: let attribute):
// guard let notification = try? managedObjectContext.existingObject(with: objectID) as? MastodonNotification,
// !notification.isDeleted,
// let status = notification.status,
// let requestUserID = dependency.context.authenticationService.activeMastodonAuthenticationBox.value?.userID
// else { return UITableViewCell() }
// let cell = tableView.dequeueReusableCell(withIdentifier: String(describing: StatusTableViewCell.self), for: indexPath) as! StatusTableViewCell
//
// // configure cell
// StatusSection.configureStatusTableViewCell(
// cell: cell,
// tableView: tableView,
// timelineContext: .notifications,
// dependency: dependency,
// readableLayoutFrame: tableView.readableContentGuide.layoutFrame,
// status: status,
// requestUserID: requestUserID,
// statusItemAttribute: attribute
// )
// cell.statusView.headerContainerView.isHidden = true // set header hide
// cell.statusView.actionToolbarContainer.isHidden = true // set toolbar hide
// cell.statusView.actionToolbarPlaceholderPaddingView.isHidden = false
// cell.delegate = statusTableViewCellDelegate
// cell.isAccessibilityElement = true
// StatusSection.configureStatusAccessibilityLabel(cell: cell)
// return cell
//
// case .bottomLoader:
// let cell = tableView.dequeueReusableCell(withIdentifier: String(describing: TimelineBottomLoaderTableViewCell.self)) as! TimelineBottomLoaderTableViewCell
// cell.startAnimating()
// return cell
// }
}
}
}
extension NotificationSection {
static func configure(
context: AppContext,
tableView: UITableView,
cell: NotificationTableViewCell,
viewModel: NotificationTableViewCell.ViewModel,
configuration: Configuration
) {
StatusSection.setupStatusPollDataSource(
context: context,
statusView: cell.notificationView.statusView
)
StatusSection.setupStatusPollDataSource(
context: context,
statusView: cell.notificationView.quoteStatusView
)
context.authenticationService.activeMastodonAuthenticationBox
.map { $0 as UserIdentifier? }
.assign(to: \.userIdentifier, on: cell.notificationView.viewModel)
.store(in: &cell.disposeBag)
cell.configure(
tableView: tableView,
viewModel: viewModel,
delegate: configuration.notificationTableViewCellDelegate
)
}
// static func configure(
// tableView: UITableView,
// cell: NotificationStatusTableViewCell,
// notification: MastodonNotification,
// dependency: NeedsDependency,
// attribute: Item.StatusAttribute
// ) {
// // configure author
// cell.configure(
// with: AvatarConfigurableViewConfiguration(
// avatarImageURL: notification.account.avatarImageURL()
// )
// )
//
// func createActionImage() -> UIImage? {
// return UIImage(
// systemName: notification.notificationType.actionImageName,
// withConfiguration: UIImage.SymbolConfiguration(
// pointSize: 12, weight: .semibold
// )
// )?
// .withTintColor(.systemBackground)
// .af.imageAspectScaled(toFit: CGSize(width: 14, height: 14))
// }
//
// cell.avatarButton.badgeImageView.backgroundColor = notification.notificationType.color
// cell.avatarButton.badgeImageView.image = createActionImage()
// cell.traitCollectionDidChange
// .receive(on: DispatchQueue.main)
// .sink { [weak cell] in
// guard let cell = cell else { return }
// cell.avatarButton.badgeImageView.image = createActionImage()
// }
// .store(in: &cell.disposeBag)
//
// // configure author name, notification description, timestamp
// let nameText = notification.account.displayNameWithFallback
// let titleLabelText: String = {
// switch notification.notificationType {
// case .favourite: return L10n.Scene.Notification.userFavoritedYourPost(nameText)
// case .follow: return L10n.Scene.Notification.userFollowedYou(nameText)
// case .followRequest: return L10n.Scene.Notification.userRequestedToFollowYou(nameText)
// case .mention: return L10n.Scene.Notification.userMentionedYou(nameText)
// case .poll: return L10n.Scene.Notification.userYourPollHasEnded(nameText)
// case .reblog: return L10n.Scene.Notification.userRebloggedYourPost(nameText)
// default: return ""
// }
// }()
//
// do {
// let nameContent = MastodonContent(content: nameText, emojis: notification.account.emojiMeta)
// let nameMetaContent = try MastodonMetaContent.convert(document: nameContent)
//
// let mastodonContent = MastodonContent(content: titleLabelText, emojis: notification.account.emojiMeta)
// let metaContent = try MastodonMetaContent.convert(document: mastodonContent)
//
// cell.titleLabel.configure(content: metaContent)
//
// if let nameRange = metaContent.string.range(of: nameMetaContent.string) {
// let nsRange = NSRange(nameRange, in: metaContent.string)
// cell.titleLabel.textStorage.addAttributes([
// .font: UIFontMetrics(forTextStyle: .headline).scaledFont(for: .systemFont(ofSize: 15, weight: .semibold), maximumPointSize: 20),
// .foregroundColor: Asset.Colors.brandBlue.color,
// ], range: nsRange)
// }
//
// } catch {
// let metaContent = PlaintextMetaContent(string: titleLabelText)
// cell.titleLabel.configure(content: metaContent)
// }
//
// let createAt = notification.createAt
// cell.timestampLabel.text = createAt.localizedSlowedTimeAgoSinceNow
// AppContext.shared.timestampUpdatePublisher
// .receive(on: DispatchQueue.main)
// .sink { [weak cell] _ in
// guard let cell = cell else { return }
// cell.timestampLabel.text = createAt.localizedSlowedTimeAgoSinceNow
// }
// .store(in: &cell.disposeBag)
//
// // configure follow request (if exist)
// if case .followRequest = notification.notificationType {
// cell.acceptButton.publisher(for: .touchUpInside)
// .sink { [weak cell] _ in
// guard let cell = cell else { return }
// cell.delegate?.notificationTableViewCell(cell, notification: notification, acceptButtonDidPressed: cell.acceptButton)
// }
// .store(in: &cell.disposeBag)
// cell.rejectButton.publisher(for: .touchUpInside)
// .sink { [weak cell] _ in
// guard let cell = cell else { return }
// cell.delegate?.notificationTableViewCell(cell, notification: notification, rejectButtonDidPressed: cell.rejectButton)
// }
// .store(in: &cell.disposeBag)
// cell.buttonStackView.isHidden = false
// } else {
// cell.buttonStackView.isHidden = true
// }
//
// // configure status (if exist)
// if let status = notification.status {
// let frame = CGRect(
// x: 0,
// y: 0,
// width: tableView.readableContentGuide.layoutFrame.width - NotificationStatusTableViewCell.statusPadding.left - NotificationStatusTableViewCell.statusPadding.right,
// height: tableView.readableContentGuide.layoutFrame.height
// )
// StatusSection.configure(
// cell: cell,
// tableView: tableView,
// timelineContext: .notifications,
// dependency: dependency,
// readableLayoutFrame: frame,
// status: status,
// requestUserID: notification.userID,
// statusItemAttribute: attribute
// )
// cell.statusContainerView.isHidden = false
// cell.containerStackView.alignment = .top
// cell.containerStackViewBottomLayoutConstraint.constant = 0
// } else {
// if case .followRequest = notification.notificationType {
// cell.containerStackView.alignment = .top
// } else {
// cell.containerStackView.alignment = .center
// }
// cell.statusContainerView.isHidden = true
// cell.containerStackViewBottomLayoutConstraint.constant = 5 // 5pt margin when no status view
// }
// }
//
// static func configureStatusAccessibilityLabel(cell: NotificationStatusTableViewCell) {
// // FIXME:
// cell.accessibilityLabel = {
// var accessibilityViews: [UIView?] = []
// accessibilityViews.append(contentsOf: [
// cell.titleLabel,
// cell.timestampLabel,
// cell.statusView
// ])
// if !cell.statusContainerView.isHidden {
// if !cell.statusView.headerContainerView.isHidden {
// accessibilityViews.append(cell.statusView.headerInfoLabel)
// }
// accessibilityViews.append(contentsOf: [
// cell.statusView.nameMetaLabel,
// cell.statusView.dateLabel,
// cell.statusView.contentMetaText.textView,
// ])
// }
// return accessibilityViews
// .compactMap { $0?.accessibilityLabel }
// .joined(separator: " ")
// }()
// }
}