连接两个节点
EasyReact 的重点就是让节点之间的数据流动起来,所以连接节点是很重要的。
如何连接两个节点
两个节点是通过变换来连接的,在源码目录 EasyReact/Classes/Core/NodeTransforms 中我们默认实现了了很多的变换,你也可以通过继承 EZRTransform 类来实现自己的变换,一旦我们创建好一个变换后,就可以通过如下方式进行连接了:
EZRMutableNode<NSNumber *> *nodeA = [EZRMutableNode value:@1];
EZRNode<NSNumber *> *nodeB = [EZRNode new];
EZRTransform *transform = [EZRTransform new];
transform.from = nodeA;
transform.to = nodeB;
NSLog(@"%@", nodeB.value); // <- @1
也可以通过 EZRNode 的 linkTo:
或者 linkTo:transform
来实现连接:
EZRMutableNode<NSNumber *> *nodeA = [EZRMutableNode value:@1];
EZRNode<NSNumber *> *nodeB = [EZRNode new];
EZRTransform *transform = [EZRTransform new];
[nodeB linkTo:nodeA transform:transform]; // <- 相当于 transform.from = nodeA; transform.to = nodeB; 请注意方向
EZRMutableNode<NSNumber *> *nodeC = [EZRMutableNode value:@2];
EZRNode<NSNumber *> *nodeD = [EZRNode new];
[nodeD linkTo:nodeC]; // <- 相当于 [nodeD linkTo:nodeC transform:[EZRTransform new]];
断开两个节点
当两个节点不再相关的时候,你需要断开两个节点,如果你还有变换的实例,可以修改 from 或者 to 的属性来断开这两个节点或者改变连接:
EZRMutableNode<NSNumber *> *nodeA = [EZRMutableNode value:@1];
EZRNode<NSNumber *> *nodeB = [EZRNode new];
EZRTransform *transform = [EZRTransform new];
[nodeB linkTo:nodeA transform:transform];
NSLog(@"%@", nodeB.value); // <- @1
nodeA.value = @2;
NSLog(@"%@", nodeB.value); // <- @2
transform.to = nil;
nodeA.value = @3;
NSLog(@"%@", nodeB.value); // <- @2,不再跟随 nodeA 的变化而变化了
没有变换的实例也没有关系,EZRNode 有removeDownstreamNode:
、removeUpstreamNode:
、removeDownstreamNodes
、removeUpstreamNodes
等多种方法来断开与其他节点的连接:
EZRMutableNode<NSNumber *> *nodeA = [EZRMutableNode value:@1];
EZRNode<NSNumber *> *nodeB = [EZRNode new];
[nodeB linkTo:nodeA];
[nodeB removeUpstreamNode:nodeA]; // <- 断开与上游 nodeA 的全部连接
[nodeA removeDownstreamNode:nodeB]; // <- 断开与下游 nodeB 的全部连接
[nodeB removeUpstreamNodes]; // <- 断开所有的上游连接
[nodeA removeDownstreamNodes]; // <- 断开所有的下游连接
隐式的连接两个节点
很多时候先创建节点再创建变换最后连接下游是我们默认的行为,为了更好的编码,我们提供了衍生变换的方式:
EZRMutableNode<NSNumber *> *nodeA = [EZRMutableNode value:@1];
EZRNode<NSNumber *> *nodeB = [nodeA fork];
它等价于:
EZRMutableNode<NSNumber *> *nodeA = [EZRMutableNode value:@1];
EZRNode<NSNumber *> *nodeB = [EZRNode new];
[nodeB linkTo:nodeA transform:[EZRTransform new]];
相应的,其他变换也都提供了衍生变换的方式:
EZRMutableNode<NSNumber *> *nodeA = [EZRMutableNode value:@1];
EZRNode<NSNumber *> *nodeB = [nodeA map:^NSNumber *(NSNumber *next){
return @(next.integerValue * 2);
}];
它对应等同于:
EZRMutableNode<NSNumber *> *nodeA = [EZRMutableNode value:@1];
EZRNode<NSNumber *> *nodeB = [EZRNode new];
EZRMapTransform *mapTransform = [[EZRMapTransform alloc] initWithMapBlock:^NSNumber *(NSNumber *next){
return @(next.integerValue * 2);
}];
[nodeB linkTo:nodeA transform:mapTransform];
这种方式更直观和简单,所以下面在介绍变换的时候,会统一使用衍生的形式来介绍。