首页 文章

RxSwift MVVM如何使用项目管理器设置视图模型?

提问于
浏览
5

Say I have the following SwiftRx (2.0.0-beta.4) MVVM situation:

我有4件事:

  • ItemListViewController

  • ItemsViewModel

  • ItemsManager

  • 项目

ItemsManager 有一个名为 items() 的函数,它将以可观察的RxSwift方式返回Items .

ItemsViewModel 目前只需要传递物品 . 稍后可能会在视图控制器的Item属性上应用显示逻辑(比如正确显示日期) .

ItemListViewController 会将项目放在一个表格中,每行一个项目 .

Item有4个属性(如标识符,日期......),它们将显示在表格行单元格中 .

How does one set it up in the ItemsViewModel and ItemsManager so that when items are added, removed, changed in the manager that they go through the ItemsViewModel?

从阅读documentation并查看Rx.playground,似乎现在使用的是RxSwift PublishSubject< Item > 或者RxSwift map ,它以某种方式订阅了经理的项目()

怎么做得好?

ItemsManager现在有这样的东西:

func items() -> Observable<Item> {
    // placeholder for now
    return [Item(identification: "123", content: ""), Item(identification: "456", content:""), Item(identification: "789", content:"")].toObservable()
}

View Model有这个:

let items = Variable(/* how to subsribe to the items in the manager? */)

1 回答

  • 8

    一个人为的解决方案,也就是说明了一般方法并且更容易理解的解决方案如下:

    import UIKit
    import RxSwift
    import RxCocoa
    
    struct Item {
    
        let identification: String
        let content: String
    }
    
    struct ItemsManager {
    
        let items: Variable<[Item]> = Variable<[Item]>(
            [Item(identification: "some id1", content: "some content"),
            Item(identification: "some id2", content: "some more content")]
        )
    }
    
    struct ItemsViewModel {
    
        let itemsManager = ItemsManager()
    
        let myItems:Observable<[String]>
    
        init() {
    
            myItems = itemsManager.items
            .map({ someArrayOfItems in
                return someArrayOfItems.map {$0.content }
            })
        }
    }
    
    class ItemListViewController: UIViewController {
    
        @IBOutlet weak var tableView: UITableView!
    
        let itemsViewModel = ItemsViewModel()
    
        let disposeBag = DisposeBag()
    
        override func viewDidLoad() {
            super.viewDidLoad()
    
            itemsViewModel.myItems
                .bindTo(tableView.rx_itemsWithCellIdentifier("itemListCell")) { (row, element, cell) in
    
                    guard let myCell: UITableViewCell = cell else {
                        return
                    }
    
                    myCell.textLabel?.text = element
                }
                .addDisposableTo(disposeBag)
    
        }
    }
    

相关问题