美文网首页RxSwift学习
RxSwift<9> —— MVVM双向绑定

RxSwift<9> —— MVVM双向绑定

作者: Gollum_ | 来源:发表于2019-10-18 10:30 被阅读0次

RxSwift 遇到tableView

  let dataOB = BehaviorSubject.init(value: self.viewModel.dataArray)
//        dataOB.bind(to: self.tableView.rx.items){(table,row,model) -> UITableViewCell in
//            let cell = table.dequeueReusableCell(withIdentifier: self.resuseID)
//            return cell as! LGTableViewCell
//        }
        
        dataOB.asObserver().bind(to: self.tableView.rx.items(cellIdentifier:self.resuseID,cellType: LGTableViewCell.self)){(row,model,cell) in
            cell.setUIData(model as! LGModel)
        }.disposed(by: disposeBag)
        
        tableView.rx.itemSelected
            .subscribe(onNext:{[weak self] index in
                
            }).disposed(by: disposeBag)
        
        tableView.rx.itemDeselected
            .subscribe(onNext:{index in
                
            }).disposed(by: disposeBag)
        
        tableView.rx.itemMoved
            .subscribe(onNext:{[weak self] (sourceIndex,destinationIndex) in
              print("从\(sourceIndex)移动到\(destinationIndex)")
            }).disposed(by: disposeBag)
  • TableView的点击、复选、新增、删除、移动全部简洁实现
  • RxSwift一旦遇上了TableView,根本不需要那些恶心的胶水代码
  • delegate & dataSource的赋值直接免去
  • 胶水代理以及数据源代理的实现(毕竟我们现在列表界面越来越多,胶水的代码的优化,太爽了)
  • 我们所有的事件订阅都在相应地方,我们更容易管理
  • 函数式回调导致我们的逻辑代码与功能代码绑定在一块,可读性更强
  • cell高度可通过代理实现
extension LGRxViewController:UITableViewDelegate {
    func tableView(_ tableView: UITableView, heightForRowAt indexPath: IndexPath) -> CGFloat {
        return 100
    }
}

分组tableView

let tableViewDataSource = RxTableViewSectionedReloadDataSource<SectionModel<String,LGSectionModel>>(configureCell: { [weak self](dataSource, tab, indexPath, model) -> LGTableViewCell in
        let cell = tab.dequeueReusableCell(withIdentifier: self?.resuseID ?? "resuseID_LGSectionViewController", for: indexPath) as! LGTableViewCell
        cell.setUISectionData(model)
        cell.selectionStyle = .none
        return cell
    },titleForHeaderInSection: { dataSource,index -> String in
        // print("数据:\(dataSource.sectionModels[index].identity)")
        return dataSource.sectionModels[index].model
    })

    /// 我们上次就是通过bind函数,这里我们变化一下
    self.data.githubData.asDriver(onErrorJustReturn: [])
        .drive(self.tableView.rx.items(dataSource: tableViewDataSource))
        .disposed(by: self.disposeBag)

MVVM双向绑定
VC中:

override func viewDidLoad() {
    super.viewDidLoad()
    self.setupUI()
    // 现在来一个需求:我们的输入框搜索 - 请求网络 - 下面tableView联动
    // UI <-> model
    self.searchBar.rx.text.orEmpty
        .bind(to: self.viewModel.searchTextOB)
        .disposed(by: disposeBag)
    
   // 数据层绑定UI
    self.viewModel.searchData.drive(self.tableView.rx.items){ (tableView, indexPath, model) -> LGTableViewCell in
        let cell = tableView.dequeueReusableCell(withIdentifier: self.resuseID) as! LGTableViewCell
        cell.nameLabel.text  = model.name
        cell.classLabel.text = model.url
        return cell
    }
    .disposed(by: disposeBag)
    
    // tittle绑定
    self.viewModel.searchData.map { (array) -> String in
        return "搜索到了 \(array.count) 条数据"
    }
    .drive(self.navigationItem.rx.title)
    .disposed(by: disposeBag)
    
    // 滑动减速绑定
    self.tableView.rx.didEndDecelerating
        .subscribe { [weak self] in
            self?.searchBar.endEditing(true)
    }.disposed(by: disposeBag)
}
  • 这里就是我们RxSwift世界里的ViewController,这才是真正的轻量化的VC,至始至终都只做一件事:建立View与ViewModel之间的绑定依赖关系
  • 通过我们搜索栏的响应,发送数据给我们的ViewModel,让它在它的世界里处理业务层,网络层数据的返回
  • 通过ViewModel响应对外,达到数据绑定到UI的效果
  • 在ViewModel里面我们运用RxSwift的高阶函数,处理逻辑

VM中

let searchTextOB = BehaviorSubject(value: "")
lazy var searchData: Driver<[LGReposityModel]> = {
    return self.searchTextOB.asObserver()
        .throttle(RxTimeInterval.milliseconds(300), scheduler: MainScheduler.instance)
        .distinctUntilChanged()
        .flatMapFirst(LGComprehensiveViewModel.resposeData)
        .asDriver(onErrorJustReturn: [])
}()
  • UI事件搜索的响应传入,通过一个懒加载的数据返回
  • 这个响应的序列通过throttle保证了相隔0.3秒发送一次事件
  • distinctUntilChanged函数保证了带宽,直到搜索字眼变动的时候才请求
  • flatMapFirst因为序列的序列,我们下沉请求,回调结果
  • asDriver包装成Drive序列,保证状态共享,主线程调度,没有错误返回

或者直接用BehaviorRelay封装数据源,在VC中绑定tableview

相关文章

  • RxSwift<9> —— MVVM双向绑定

    RxSwift 遇到tableView TableView的点击、复选、新增、删除、移动全部简洁实现 RxSwif...

  • RxSwift-MVVM双向绑定

    RxSwift 篇章已经接近尾声,回首这个历程很累但很充实:白天备课,晚上VIP上课!忙里偷闲写下了这个篇章。可以...

  • RxSwift(24)——MVVM双向绑定

    在项目开发中,除了常用的MVC开发模式,还有一种常用的开发模式就是MVVM。 1.什么是MVVM?MVVM是Mod...

  • 双向数据绑定

    双向数据绑定 双向数据绑定基于MVVM框架,vue属于MVVM框架 MVVM:M等于model,V等于view,即...

  • angular双向绑定

    MVVM的核心机制就是双向绑定。React、Vue、Angular的双向绑定,都是基于MVVM的设计模式。 双向绑...

  • Angular学习笔记-双向绑定

    Angular和Vue一样都是MVVM的框架,MVVM的核心机制就是双向绑定。 双向绑定将属性绑定与事件绑定结合在...

  • Vue2.0原理与MVVM的实现

    剖析Vue原理&实现双向绑定MVVM vue源码 双向绑定 -- MVVM 目前几种主流的MVC框架都实现了单向数...

  • Vue2 数据双向绑定原理解析-简易版(个人笔记)

    一、什么是 MVVM 数据双向绑定 MVVM 数据双向绑定主要是指:数据变化更新视图,视图变化更新数据,如下图所示...

  • MVVM双向绑定

  • vue双向数据绑定

    剖析Vue原理、实现双向绑定MVVM 几种实现双向绑定的做法 目前几种主流的mvc(vm)框架都实现了单向数据绑定...

网友评论

    本文标题:RxSwift<9> —— MVVM双向绑定

    本文链接:https://www.haomeiwen.com/subject/yrtimctx.html