rxswift 是時間監(jiān)聽框架渔呵,每一個事件比如文本的改變,按鈕的點擊或者網(wǎng)絡(luò)請求的結(jié)束砍鸠,每一個事件可以看成一個管道sequence扩氢,事件從管道流程,然后只需要監(jiān)聽這個管道就可以實現(xiàn)事件的監(jiān)聽
- 核心思想是Observable爷辱,即可監(jiān)聽的序列
- 通過DisposeBag來取消監(jiān)聽录豺,所有監(jiān)聽后面都會增加.addDisposableTo(bag)
-
控件的監(jiān)聽
a. UISliderde 的監(jiān)聽
slider.rx.value.asObservable() .subscribe(onNext: { print("當(dāng)前值為:\($0)") }) .disposed(by: disposeBag)
- 任何對象通過asObservable都可以實現(xiàn)監(jiān)聽,比如collectionView.mj_footer!.rx.refreshing.asObservable()
將UISliderde中的值賦值給UIStepper
slider.rx.value .map{ Double($0) } //由于slider值為Float類型饭弓,而stepper的stepValue為Double類型双饥,因此需要轉(zhuǎn)換 .bind(to: stepper.rx.stepValue) .disposed(by: disposeBag)
-
表中的數(shù)據(jù)刷新
let item = Observable<[SocilaModel]>.just(self.dataArr!) //或者使用 let item = Observable.from(optional: self.dataArr!)
item.bind(to: self.listTab.rx.items) { (tableView, row, element) in let cell = tableView.dequeueReusableCell(withIdentifier: "cell") as! SecondSocialTableViewCell cell.leftImageView.kf.setImage(with: URL(string: element.image_list ?? "")) cell.titleLabel.text = element.theme_name cell.descripLabel.text = element.info //cell中按鈕點擊事件訂閱 cell.RXButton.rx.tap.asDriver() .drive(onNext: { [weak self] in self?.showAlert(title: "\(row)", message: "哈哈哈") }).disposed(by: cell.disposeBag) return cell } .disposed(by: self.disposeBag) } }
3.按鈕的點擊監(jiān)聽
button1.rx.tap.subscribe { (event) in
self.button1.setTitle("按鈕1", for: .normal)
print("button1")}.addDisposableTo(self.disposeBag)
button2.rx.tap.subscribe { (event) in
self.textField2.text = "按鈕2被點擊了"
}.addDisposableTo(self.disposeBag)
4.監(jiān)聽UITextfield的文字改變
a.使用on方法實現(xiàn)
textField1.rx.text.subscribe { (event: Event<String?>) in
//將UITextField文字改變的內(nèi)容顯示在Label中
self.label1.text = event.element!
print(event.element!!)}.addDisposableTo(self.disposeBag)
textField2.rx.text.subscribe { (event: Event<String?>) in
print(event.element)//報警告 //輸出: Optional(Optional("jun"))
}.addDisposableTo(self.disposeBag)
b.使用onNext方法實現(xiàn)
textField1.rx.text.subscribe(onNext: { (str: String?) in
self.label1.text = str!}).addDisposableTo(self.disposeBag)
c.多個textField的監(jiān)聽,并通過監(jiān)聽改變button 的透明度
Observable.combineLatest(phoneTextField.rx.text, passwordCodeTextField.rx.text)
.map({ (userName, password) in
if (userName?.count ?? 0) >= 11 && (password?.count ?? 0) >= 4 {
return CGFloat(1)
}
return CGFloat(0.2)
})
.bind(to: loginButton.rx.alpha)
.disposed(by: disposeBag)
-
Driver的使用示启,主要比如多次請求只需要處理一次數(shù)據(jù)
序列需要滿足下面的條件才可以使用:
- 不會產(chǎn)生 error 事件
- 一定在主線程監(jiān)聽(MainScheduler)
- 共享狀態(tài)變化(shareReplayLatestWhileConnected)
使用場景:
- Driver 最常使用的場景應(yīng)該就是需要用序列來驅(qū)動應(yīng)用程序的情況了兢哭,比如通過 CoreData 模型驅(qū)動 UI;使用一個 UI 元素值(綁定)來驅(qū)動另一個 UI 元素值
- 與普通的操作系統(tǒng)驅(qū)動程序一樣,如果出現(xiàn)序列錯誤夫嗓,應(yīng)用程序?qū)⑼V鬼憫?yīng)用戶輸入迟螺。
- 在主線程上觀察到這些元素也是極其重要的,因為 UI 元素和應(yīng)用程序邏輯通常不是線程安全的舍咖。
- 此外矩父,使用構(gòu)建 Driver 的可觀察的序列,它是共享狀態(tài)變化排霉。
使用案例
let result = inputTF.rx.text.orEmpty
.asDriver()
.flatMap { return self.dealwithData(inputText: $0)
.asDriver(onErrorJustReturn: "檢測到了錯誤事件") }
第一次訂閱
//第一次訂閱,并把內(nèi)容綁定到另一個UILabel上
result.map{ "長度:\( ($0 as! String).count )" }
.drive(self.textLabel.rx.text)
.disposed(by: disposeBag)
//第二次訂閱,并把內(nèi)容綁定到另一個UIButton上
result.map { "\($0 as! String)"}
.drive(self.btn.rx.title())
.disposed(by: disposeBag)
-
改變label 中文字
label1.rx.observe(String.self, "text") .subscribe(onNext: { (str: String?) in print(str!)}).addDisposableTo(disposeBag) label2.rx.observe(CGRect.self, "frame") .subscribe(onNext: { (rect: CGRect?) in print(rect!.width)}).addDisposableTo(disposeBag)
7.監(jiān)聽UIScrollView的滾動
scrollView.contentSize = CGSize(width: 1000, height: 0)
scrollView.rx.contentOffset.subscribe(onNext: { (point : CGPoint) in
print(point)}).addDisposableTo(disposeBag)