XCEFunctionalState 4.0.1

XCEFunctionalState 4.0.1

测试已测试
语言语言 SwiftSwift
许可证 MIT
发布最后发布2018年4月
SPM支持 SPM

Maintained by Maxim Khatskevich.



  • Maxim Khatskevich

GitHub tag CocoaPods CocoaPods license

介绍

将任何对象转换为离散系统,并声明式地描述其状态。

如何安装

推荐使用 CocoaPods 安装。

pod 'XCEFunctionalState', '~> 2.8'

它是如何工作的

此库允许通过定义一组不同的状态,并将这些状态应用于对象来将其转换为 离散系统

如何使用

此库的典型用例是使用它来重新配置 UIView 及其子类实例,以便在您的应用程序状态更改时重新配置。

状态

每个状态都定义了其应用的规则以及如何更新(在它被请求应用而已处于当前状态时),以及一系列操作转换(默认为立即转换)。

有状态的

例如,我们有一个名为SearchView的类,它代表一个文本字段视图和一个启动搜索过程的按钮。它必须遵循有状态的协议才能成为一个独立的系统。

import XCEFunctionalState

class SearchView: Stateful
{
    let keyword = UITextField()
    let start = UIButton()
    
    private(set)
    lazy
    var state: Dispatcher<MyView> = Dispatcher(for: self)
}

为了描述类的状态,在这个类内部定义一个类级别函数(它的名称将被解释为状态名称),该函数返回一个对该类的状态

例如,让我们为我们的SearchView类定义一个awaiting状态,其中keyword文本字段和start按钮都可以使用并且可以供用户输入。请注意,我们可以定义任意多的输入参数作为该函数的参数,这为我们提供了从外部将任何类型的值传递到状态配置闭包的机会。下面是如何传递keyword字段的默认值。

extension SearchView
{
    static
    func awaiting(with keyword: String) -> State<SearchView>
    {
        return state{

            $0.keyword.text = keyword
            $0.keyword.isEnabled = true
            $0.start.isEnabled = true
        }
    }
}

当用户输入了搜索关键字并按下start按钮后,我们可能想要在搜索进行时锁定这些控件。要做到这一点,我们可能需要将locked状态应用于搜索视图,这可以声明如下

extension SearchView
{
    static
    func locked() -> State<SearchView>
    {
        return state{

            $0.keyword.isEnabled = false
            $0.start.isEnabled = false
        }
    }
}

稍后,我们可以将类中声明的任何状态应用于这个类的实例,如下所示

let transition: Transition<SearchView> = ... // define transition
let view = SearchView()

view.state.apply{ $0.awaiting(with: "something") }
view.state.apply{ $0.awaiting(with: "another value") } // no effect
view.state.apply(via: transition, MyView.locked()){ /* completion*/ }
//...
view.state.apply{ $0.awaiting(with: "after search") }

默认情况下,所有变异都是立即应用的。当使用基于UIView的类工作时,使用动画来应用更改是常见的,并且转换类型提供了完全的控制。

有状态的协议还允许定义在应用状态时应默认使用的转换,但在状态定义中不提供特定的转换。

extension SearchView
{
    static
    var defaultOnSetTransition: Transition<SearchView> = {
    	
    	(view, mutations, completion) in

        view.alpha = 0.0

        //---

        mutations() // this is closure from the state

        //---

        UIView.animate(
        	withDuration: 1.0,
            animations: { v.alpha = 1.0 },
            completion: completion
        )
    }
    
    static
    var defaultOnUpdateTransition: Transition<SearchView> = {
      
      //...
    }
}

上例中的`defaultOnSetTransition`展示了隐藏整个视图的转换,然后应用新状态中的变异,最后使用动画使整个视图再次可见。或者,如果需要,我们可以在`UIImageView.animate(…)`调用中调用`mutations()`来在淡入动画中动画实际变异。

与Objective-C的互操作性

为了使代码尽可能简洁、易于理解,并保持编译时的类型安全,这个库依赖于Swift语言的先进功能,如泛型和 closures 简写参数名称,因此它**不**旨在与Objective-C兼容。