Skip to content

Commit

Permalink
添加点击删除消息功能
Browse files Browse the repository at this point in the history
  • Loading branch information
Finb committed Jan 2, 2025
1 parent 5766706 commit 1b48b49
Show file tree
Hide file tree
Showing 3 changed files with 83 additions and 19 deletions.
39 changes: 27 additions & 12 deletions Controller/MessageListViewController.swift
Original file line number Diff line number Diff line change
Expand Up @@ -49,6 +49,8 @@ class MessageListViewController: BaseViewController<MessageListViewModel> {

private var expandedGroup: Set<String> = []

private let itemDeleteInGroupRelay = PublishRelay<MessageItemModel>()

lazy var tableView: UITableView = {
let tableView = UITableView()
tableView.separatorStyle = .none
Expand Down Expand Up @@ -138,8 +140,8 @@ class MessageListViewController: BaseViewController<MessageListViewModel> {
return UITableViewCell()
}
cell.tapAction = { [weak self, weak cell] message, sourceView in
guard let self else { return }
self.alertMessage(message: message.attributedText?.string ?? "", sourceView: sourceView)
guard let self, let cell else { return }
self.alertMessage(message: message, sourceView: sourceView, sourceCell: cell)
}
cell.message = message
return cell
Expand Down Expand Up @@ -168,8 +170,8 @@ class MessageListViewController: BaseViewController<MessageListViewModel> {
self.tableView.dataSource?.tableView?(self.tableView, commit: .delete, forRowAt: indexPath)
}
cell.tapAction = { [weak self, weak cell] message, sourceView in
guard let self else { return }
self.alertMessage(message: message.attributedText?.string ?? "", sourceView: sourceView)
guard let self, let cell else { return }
self.alertMessage(message: message, sourceView: sourceView, sourceCell: cell)
}
cell.cellData = (title, totalCount, messages)
cell.isExpanded = self.expandedGroup.contains(title)
Expand All @@ -191,6 +193,7 @@ class MessageListViewController: BaseViewController<MessageListViewModel> {
refresh: tableView.refreshControl!.rx.controlEvent(.valueChanged).asDriver(),
loadMore: tableView.mj_footer!.rx.refresh.asDriver(),
itemDelete: tableView.rx.modelDeleted(MessageListCellItem.self).asDriver(),
itemDeleteInGroup: itemDeleteInGroupRelay.asDriver(onErrorDriveWith: .empty()),
delete: getBatchDeleteDriver(),
groupToggleTap: groupBtn.rx.tap.asDriver(),
searchText: navigationItem.searchController!.searchBar.rx.text.asObservable()
Expand Down Expand Up @@ -277,18 +280,30 @@ class MessageListViewController: BaseViewController<MessageListViewModel> {
.asDriver(onErrorDriveWith: .empty())
}

private func alertMessage(message: String, sourceView: UIView) {
private func alertMessage(message: MessageItemModel, sourceView: UIView, sourceCell: UITableViewCell) {
let alertController = UIAlertController(title: nil, message: nil, preferredStyle: .actionSheet)
let copyAction = UIAlertAction(title: NSLocalizedString("CopyAll"), style: .default, handler: { [weak self]

// 复制
alertController.addAction(UIAlertAction(title: NSLocalizedString("Copy2"), style: .default, handler: { [weak self]
(_: UIAlertAction) in
UIPasteboard.general.string = message
UIPasteboard.general.string = message.attributedText?.string
self?.showSnackbar(text: NSLocalizedString("Copy"))
})

let cancelAction = UIAlertAction(title: NSLocalizedString("Cancel"), style: .cancel, handler: { _ in })
}))
// 删除
alertController.addAction(UIAlertAction(title: NSLocalizedString("removeMessage"), style: .destructive, handler: { [weak self]
(_: UIAlertAction) in
guard let self, let indexPath = self.tableView.indexPath(for: sourceCell) else { return }
if sourceCell is MessageTableViewCell {
// 单个消息,把cell删除
self.tableView.dataSource?.tableView?(self.tableView, commit: .delete, forRowAt: indexPath)
} else if sourceCell is MessageGroupTableViewCell {
// 群组消息,只能删除群组中需删除的消息
self.itemDeleteInGroupRelay.accept(message)
}
}))
// 取消
alertController.addAction(UIAlertAction(title: NSLocalizedString("Cancel"), style: .cancel, handler: { _ in }))

alertController.addAction(copyAction)
alertController.addAction(cancelAction)
if UIDevice.current.userInterfaceIdiom == .pad {
alertController.popoverPresentationController?.sourceView = sourceView.superview
alertController.popoverPresentationController?.sourceRect = sourceView.frame
Expand Down
59 changes: 53 additions & 6 deletions Controller/MessageListViewModel.swift
Original file line number Diff line number Diff line change
Expand Up @@ -34,6 +34,8 @@ class MessageListViewModel: ViewModel, ViewModelType {
var loadMore: Driver<Void>
/// 删除
var itemDelete: Driver<MessageListCellItem>
/// 删除群组中某一条消息
var itemDeleteInGroup: Driver<MessageItemModel>
/// 批量删除
var delete: Driver<MessageDeleteType>
/// 切换群组和列表显示样式
Expand Down Expand Up @@ -162,12 +164,7 @@ class MessageListViewModel: ViewModel, ViewModelType {

for i in startIndex..<endIndex {
let group = groups[i].group
let messageResult: Results<Message>
if let group {
messageResult = results.filter("group == %@", group)
} else {
messageResult = results.filter("group == nil")
}
let messageResult = getMessages(in: results, group: group)

var messages: [MessageItemModel] = []
for i in 0..<min(messageResult.count, 5) {
Expand All @@ -184,6 +181,15 @@ class MessageListViewModel: ViewModel, ViewModelType {
page += 1
return items
}

/// 使用 groupName 获取 messages
func getMessages(in results: Results<Message>, group: String?) -> Results<Message> {
if let group {
return results.filter("group == %@", group)
} else {
return results.filter("group == nil")
}
}

private func getNextPage() -> [MessageListCellItem] {
if case .group = self.sourceType {
Expand Down Expand Up @@ -334,6 +340,47 @@ class MessageListViewModel: ViewModel, ViewModelType {

}).disposed(by: rx.disposeBag)

// 删除群组中某一条消息
input.itemDeleteInGroup.drive(onNext: { [weak self] model in
guard let self, let results else { return }

guard var section = messagesRelay.value.first else {
return
}

// 删除数据库里的 message
if let realm = try? Realm(),
let message = realm.objects(Message.self).filter("id == %@", model.id).first
{
try? realm.write {
realm.delete(message)
}
}

if let index = section.messages.firstIndex(where: { item in
if case .messageGroup(_, _, let messages) = item {
return messages.contains { item in
return item.id == model.id
}
}
return false
}) {
// 用最新的数据,重新生成 cellItem
if case .messageGroup(let name, _, var messages) = section.messages[index] {
let messagesResult = self.getMessages(in: results, group: messages.first?.group)
messages = messagesResult.prefix(5).map { MessageItemModel(message: $0) }
if messages.count == 0 {
section.messages.remove(at: index)
} else {
section.messages[index] = .messageGroup(name: name, totalCount: messagesResult.count, messages: messages)
}
}
}

messagesRelay.accept([section])

}).disposed(by: rx.disposeBag)

// 批量删除
input.delete.drive(onNext: { [weak self] type in
guard let strongSelf = self else { return }
Expand Down
4 changes: 3 additions & 1 deletion Model/MessageSection.swift
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@ enum MessageListCellItem: Equatable {
/// 一组消息,可以收缩折叠
case messageGroup(name: String, totalCount: Int, messages: [MessageItemModel])

// 确定 cell 内部是否需要更新
static func == (lhs: Self, rhs: Self) -> Bool {
switch (lhs, rhs) {
case (.message(let l), .message(let r)):
Expand Down Expand Up @@ -46,12 +47,13 @@ enum MessageListCellItem: Equatable {
extension MessageListCellItem: IdentifiableType {
typealias Identity = String

// 确定整个 cell 是否删除或替换
var identity: String {
switch self {
case .message(let model):
return "list_\(model.id)"
case .messageGroup(_, _, let messages):
return "group_\(messages.first?.id ?? "")"
return "group_\(messages.first?.group ?? NSLocalizedString("Default"))"
}
}
}
Expand Down

0 comments on commit 1b48b49

Please sign in to comment.