All Projects → kean → Rxnuke

kean / Rxnuke

Licence: mit
RxSwift extensions for Nuke

Programming Languages

swift
15916 projects

Labels

Projects that are alternatives of or similar to Rxnuke

Rxmarvel
Playing around marvel public API with RxSwift, Argo, Alamofire
Stars: ✭ 86 (-37.68%)
Mutual labels:  rxswift
Rxalamofire
RxSwift wrapper around the elegant HTTP networking in Swift Alamofire
Stars: ✭ 1,503 (+989.13%)
Mutual labels:  rxswift
Xcoordinator
🎌 Powerful navigation library for iOS based on the coordinator pattern
Stars: ✭ 1,752 (+1169.57%)
Mutual labels:  rxswift
Rxstorekit
StoreKit library for RxSwift
Stars: ✭ 96 (-30.43%)
Mutual labels:  rxswift
Observablearray Rxswift
An array that can emit messages of elements and diffs on it's changing.
Stars: ✭ 108 (-21.74%)
Mutual labels:  rxswift
Rxflow
RxFlow is a navigation framework for iOS applications based on a Reactive Flow Coordinator pattern
Stars: ✭ 1,589 (+1051.45%)
Mutual labels:  rxswift
Rxbluetoothkit
iOS & OSX Bluetooth library for RxSwift
Stars: ✭ 1,213 (+778.99%)
Mutual labels:  rxswift
Rxcorelocation
RxCoreLocation is a reactive abstraction to manage Core Location.
Stars: ✭ 132 (-4.35%)
Mutual labels:  rxswift
Rxgithub
An example of MVVM using RxSwift and Swinject (DI)
Stars: ✭ 109 (-21.01%)
Mutual labels:  rxswift
Bark
Bark is an iOS App which allows you to push customed notifications to your iPhone
Stars: ✭ 2,371 (+1618.12%)
Mutual labels:  rxswift
Rerxswift
ReRxSwift: RxSwift bindings for ReSwift
Stars: ✭ 97 (-29.71%)
Mutual labels:  rxswift
Boilerplate
Swift 4 and Using MVVM architecture(Rxswfit + Moya) to implement Github client demo.
Stars: ✭ 102 (-26.09%)
Mutual labels:  rxswift
Rxasdatasources
RxDataSource for AsyncDisplayKit/Texture
Stars: ✭ 114 (-17.39%)
Mutual labels:  rxswift
Qiitawithfluxsample
A sample project uses Flux and MVVM features with RxSwift.
Stars: ✭ 94 (-31.88%)
Mutual labels:  rxswift
Easyreact
Are you confused by the functors, applicatives, and monads in RxSwift and ReactiveCocoa? It doesn't matter, the concepts are so complicated that not many developers actually use them in normal projects. Is there an easy-to-use way to use reactive programming? EasyReact is born for this reason.
Stars: ✭ 1,616 (+1071.01%)
Mutual labels:  rxswift
Rxkeyboard
Reactive Keyboard in iOS
Stars: ✭ 1,246 (+802.9%)
Mutual labels:  rxswift
Rxcodable
RxSwift wrapper for Codable
Stars: ✭ 110 (-20.29%)
Mutual labels:  rxswift
Reduxmoviedb
🎥 See the upcoming movies! ReSwift + RxSwift 💖 Hacktoberfest 🎃
Stars: ✭ 137 (-0.72%)
Mutual labels:  rxswift
Rxspritekit
👾 Reactive Extensions for SpriteKit
Stars: ✭ 131 (-5.07%)
Mutual labels:  rxswift
Moyamapper
快速解析模型工具,支持RxSwift。同时支持缓存功能 【相关手册 https://MoyaMapper.github.io 】
Stars: ✭ 115 (-16.67%)
Mutual labels:  rxswift

This repository contains RxSwift extensions for Nuke as well as examples of common use cases solved by Rx.

Use Cases

Getting Started

Usage

RxNuke provides a set of reactive extensions for Nuke:

extension Reactive where Base: ImagePipeline {
    public func loadImage(with url: URL) -> Single<ImageResponse>
    public func loadImage(with request: ImageRequest) -> Single<ImageResponse>
}

A Single is a variation of Observable that, instead of emitting a series of elements, is always guaranteed to emit either a single element or an error. The common use case of Single is to wrap HTTP requests. See Traits for more info.

Here's a basic example where we load an image and display the result on success:

ImagePipeline.shared.rx.loadImage(with: url)
    .subscribe(onSuccess: { imageView.image = $0.image })
    .disposed(by: disposeBag)

Going From Low to High Resolution

Suppose you want to show users a high-resolution, slow-to-download image. Rather than let them stare a placeholder for a while, you might want to quickly download a smaller thumbnail first.

You can implement this using concat operator which results in a serial execution. It would first start a thumbnail request, wait until it finishes, and only then start a request for a high-resolution image.

Observable.concat(pipeline.rx.loadImage(with: lowResUrl).orEmpty,
                  pipeline.rx.loadImage(with: highResUtl).orEmpty)
    .subscribe(onNext: { imageView.image = $0.image })
    .disposed(by: disposeBag)

orEmpty is a custom property which ignores errors and completes the sequence instead (equivalent to func catchErrorJustComplete() from RxSwiftExt.

extension RxSwift.PrimitiveSequence {
    public var orEmpty: Observable<Element> {
        return self.asObservable().catchError { _ in .empty() }
    }
}

Loading the First Available Image

Suppose you have multiple URLs for the same image. For instance, you might have uploaded an image taken from the camera. In such case, it would be beneficial to first try to get the local URL, and if that fails, try to get the network URL. It would be a shame to download the image that we may have already locally.

This use case is very similar Going From Low to High Resolution, but an addition of .take(1) guarantees that we stop execution as soon as we receive the first result.

Observable.concat(pipeline.rx.loadImage(with: localUrl).orEmpty,
                  pipeline.rx.loadImage(with: networkUrl).orEmpty)
    .take(1)
    .subscribe(onNext: { imageView.image = $0.image })
    .disposed(by: disposeBag)

Load Multiple Images, Display All at Once

Suppose you want to load two icons for a button, one icon for .normal state and one for .selected state. Only when both icons are loaded you can show the button to the user. This can be done using a combineLatest operator:

Observable.combineLatest(pipeline.rx.loadImage(with: iconUrl).asObservable(),
                         pipeline.rx.loadImage(with: iconSelectedUrl).asObservable())
    .subscribe(onNext: { icon, iconSelected in
        button.isHidden = false
        button.setImage(icon.image, for: .normal)
        button.setImage(iconSelected.image, for: .selected)
    }).disposed(by: disposeBag)

Showing Stale Image While Validating It

Suppose you want to show users a stale image stored in a disk cache (Foundation.URLCache) while you go to the server to validate it. This use case is actually similar to Going From Low to High Resolution.

let cacheRequest = URLRequest(url: imageUrl, cachePolicy: .returnCacheDataDontLoad)
let networkRequest = URLRequest(url: imageUrl, cachePolicy: .useProtocolCachePolicy)

Observable.concat(pipeline.rx.loadImage(with: ImageRequest(urlRequest: cacheRequest).orEmpty,
                  pipeline.rx.loadImage(with: ImageRequest(urlRequest: networkRequest)).orEmpty)
    .subscribe(onNext: { imageView.image = $0.image })
    .disposed(by: disposeBag)

See Image Caching to learn more about HTTP cache

Auto Retry

Auto-retry with an exponential backoff of other delay options (including immediate retry when a network connection is re-established) using smart retry.

pipeline.rx.loadImage(with: request).asObservable()
    .retry(3, delay: .exponential(initial: 3, multiplier: 1, maxDelay: 16))
    .subscribe(onNext: { imageView.image = $0.image })
    .disposed(by: disposeBag)

Tracking Activities

Suppose you want to show an activity indicator while waiting for an image to load. Here's how you can do it using ActivityIndicator class provided by RxSwiftUtilities:

let isBusy = ActivityIndicator()

pipeline.rx.loadImage(with: imageUrl)
    .trackActivity(isBusy)
    .subscribe(onNext: { imageView.image = $0.image })
    .disposed(by: disposeBag)

isBusy.asDriver()
    .drive(activityIndicator.rx.isAnimating)
    .disposed(by: disposeBag)

In a Table or Collection View

Here's how you can integrate the code provided in the previous examples into your table or collection view cells:

final class ImageCell: UICollectionViewCell {
    private var imageView: UIImageView!
    private var disposeBag = DisposeBag()

    // <.. create an image view using your preferred way ..>

    func display(_ image: Single<ImageResponse>) {

        // Create a new dispose bag, previous dispose bag gets deallocated
        // and cancels all previous subscriptions.
        disposeBag = DisposeBag()

        imageView.image = nil

        // Load an image and display the result on success.
        image.subscribe(onSuccess: { [weak self] response in
            self?.imageView.image = response.image
        }).disposed(by: disposeBag)
    }
}

Requirements

RxNuke Swift Xcode Platforms
RxNuke 1.0 Swift 5.1 Xcode 11.0 iOS 11.0 / watchOS 4.0 / macOS 10.13 / tvOS 11.0
RxNuke 0.8 Swift 4.2 – 5.0 Xcode 10.1 – 10.2 iOS 10.0 / watchOS 3.0 / macOS 10.12 / tvOS 10.0
RxNuke 0.7 Swift 4.0 – 4.2 Xcode 9.2 – 10.1 iOS 9.0 / watchOS 2.0 / macOS 10.10 / tvOS 9.0

License

RxNuke is available under the MIT license. See the LICENSE file for more info.

Note that the project description data, including the texts, logos, images, and/or trademarks, for each open source project belongs to its rightful owner. If you wish to add or remove any projects, please contact us at [email protected].