Revert "[ASLayoutSpec] Use childrenMap directly to prevent creating an NSArray within ASDK Part 2 (#2021)"

This reverts commit d5a7c19522.
This commit is contained in:
Michael Schneider
2016-08-02 10:10:36 -07:00
parent d5a7c19522
commit d5cbe33686
11 changed files with 57 additions and 185 deletions

View File

@@ -214,7 +214,6 @@
69E1006F1CA89CB600D88C1B /* ASEnvironmentInternal.mm in Sources */ = {isa = PBXBuildFile; fileRef = 69E1006A1CA89CB600D88C1B /* ASEnvironmentInternal.mm */; };
69E100701CA89CB600D88C1B /* ASEnvironmentInternal.mm in Sources */ = {isa = PBXBuildFile; fileRef = 69E1006A1CA89CB600D88C1B /* ASEnvironmentInternal.mm */; };
69F10C871C84C35D0026140C /* ASRangeControllerUpdateRangeProtocol+Beta.h in Headers */ = {isa = PBXBuildFile; fileRef = 69F10C851C84C35D0026140C /* ASRangeControllerUpdateRangeProtocol+Beta.h */; settings = {ATTRIBUTES = (Public, ); }; };
69F6058D1D3DA27E00C8CA38 /* ASLayoutSpec+Private.h in Headers */ = {isa = PBXBuildFile; fileRef = 69F6058C1D3DA27E00C8CA38 /* ASLayoutSpec+Private.h */; };
7630FFA81C9E267E007A7C0E /* ASVideoNode.h in Headers */ = {isa = PBXBuildFile; fileRef = AEEC47DF1C20C2DD00EC1693 /* ASVideoNode.h */; settings = {ATTRIBUTES = (Public, ); }; };
764D83D51C8EA515009B4FB8 /* AsyncDisplayKit+Debug.h in Headers */ = {isa = PBXBuildFile; fileRef = 764D83D21C8EA515009B4FB8 /* AsyncDisplayKit+Debug.h */; settings = {ATTRIBUTES = (Public, ); }; };
764D83D61C8EA515009B4FB8 /* AsyncDisplayKit+Debug.m in Sources */ = {isa = PBXBuildFile; fileRef = 764D83D31C8EA515009B4FB8 /* AsyncDisplayKit+Debug.m */; };
@@ -966,7 +965,6 @@
69E100691CA89CB600D88C1B /* ASEnvironmentInternal.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = ASEnvironmentInternal.h; sourceTree = "<group>"; };
69E1006A1CA89CB600D88C1B /* ASEnvironmentInternal.mm */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.objcpp; path = ASEnvironmentInternal.mm; sourceTree = "<group>"; };
69F10C851C84C35D0026140C /* ASRangeControllerUpdateRangeProtocol+Beta.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = "ASRangeControllerUpdateRangeProtocol+Beta.h"; sourceTree = "<group>"; };
69F6058C1D3DA27E00C8CA38 /* ASLayoutSpec+Private.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = "ASLayoutSpec+Private.h"; sourceTree = "<group>"; };
6BDC61F51978FEA400E50D21 /* AsyncDisplayKit.h */ = {isa = PBXFileReference; explicitFileType = sourcecode.c.h; path = AsyncDisplayKit.h; sourceTree = "<group>"; };
764D83D21C8EA515009B4FB8 /* AsyncDisplayKit+Debug.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = "AsyncDisplayKit+Debug.h"; sourceTree = "<group>"; };
764D83D31C8EA515009B4FB8 /* AsyncDisplayKit+Debug.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = "AsyncDisplayKit+Debug.m"; sourceTree = "<group>"; };
@@ -1472,8 +1470,6 @@
044285051BAA63FE00D16268 /* ASBatchFetching.h */,
044285061BAA63FE00D16268 /* ASBatchFetching.m */,
251B8EF61BBB3D690087C538 /* ASDataController+Subclasses.h */,
8B0768B11CE752EC002E1453 /* ASDefaultPlaybackButton.h */,
8B0768B21CE752EC002E1453 /* ASDefaultPlaybackButton.m */,
AEB7B0181C5962EA00662EF4 /* ASDefaultPlayButton.h */,
AEB7B0191C5962EA00662EF4 /* ASDefaultPlayButton.m */,
058D0A08195D050800B7D73C /* ASDisplayNode+AsyncDisplay.mm */,
@@ -1482,17 +1478,16 @@
DE6EA3211C14000600183B10 /* ASDisplayNode+FrameworkPrivate.h */,
058D0A0B195D050800B7D73C /* ASDisplayNode+UIViewBridge.mm */,
058D0A0C195D050800B7D73C /* ASDisplayNodeInternal.h */,
69E100691CA89CB600D88C1B /* ASEnvironmentInternal.h */,
69E1006A1CA89CB600D88C1B /* ASEnvironmentInternal.mm */,
68B8A4DB1CBD911D007E4543 /* ASImageNode+AnimatedImagePrivate.h */,
058D0A0D195D050800B7D73C /* ASImageNode+CGExtras.h */,
058D0A0E195D050800B7D73C /* ASImageNode+CGExtras.m */,
ACF6ED431B17847A00DA7C62 /* ASInternalHelpers.h */,
ACF6ED441B17847A00DA7C62 /* ASInternalHelpers.m */,
69F6058C1D3DA27E00C8CA38 /* ASLayoutSpec+Private.h */,
ACF6ED451B17847A00DA7C62 /* ASLayoutSpecUtilities.h */,
E52405B41C8FEF16004DC8E7 /* ASLayoutTransition.h */,
E52405B21C8FEF03004DC8E7 /* ASLayoutTransition.mm */,
69E100691CA89CB600D88C1B /* ASEnvironmentInternal.h */,
69E1006A1CA89CB600D88C1B /* ASEnvironmentInternal.mm */,
058D0A0D195D050800B7D73C /* ASImageNode+CGExtras.h */,
058D0A0E195D050800B7D73C /* ASImageNode+CGExtras.m */,
68B8A4DB1CBD911D007E4543 /* ASImageNode+AnimatedImagePrivate.h */,
ACF6ED431B17847A00DA7C62 /* ASInternalHelpers.h */,
ACF6ED441B17847A00DA7C62 /* ASInternalHelpers.m */,
ACF6ED451B17847A00DA7C62 /* ASLayoutSpecUtilities.h */,
0442850B1BAA64EC00D16268 /* ASMultidimensionalArrayUtils.h */,
0442850C1BAA64EC00D16268 /* ASMultidimensionalArrayUtils.mm */,
CC3B20811C3F76D600798563 /* ASPendingStateController.h */,
@@ -1510,6 +1505,8 @@
CC3B20881C3F7A5400798563 /* ASWeakSet.m */,
DBC452D91C5BF64600B16017 /* NSArray+Diffing.h */,
DBC452DA1C5BF64600B16017 /* NSArray+Diffing.m */,
8B0768B11CE752EC002E1453 /* ASDefaultPlaybackButton.h */,
8B0768B21CE752EC002E1453 /* ASDefaultPlaybackButton.m */,
);
path = Private;
sourceTree = "<group>";
@@ -1743,7 +1740,6 @@
B350625B1B010F070018CF92 /* ASEqualityHelpers.h in Headers */,
680346941CE4052A0009FEB4 /* ASNavigationController.h in Headers */,
B350621B1B010EFD0018CF92 /* ASFlowLayoutController.h in Headers */,
69F6058D1D3DA27E00C8CA38 /* ASLayoutSpec+Private.h in Headers */,
B350621D1B010EFD0018CF92 /* ASHighlightOverlayLayer.h in Headers */,
C78F7E2B1BF7809800CDEAFC /* ASTableNode.h in Headers */,
AC7A2C181BDE11DF0093FE1A /* ASTableViewInternal.h in Headers */,

View File

@@ -2981,15 +2981,6 @@ static const char *ASDisplayNodeDrawingPriorityKey = "ASDrawingPriority";
}
}
#pragma mark - NSFastEnumeration
- (NSUInteger)countByEnumeratingWithState:(NSFastEnumerationState *)state
objects:(id __unsafe_unretained [])stackbuf
count:(NSUInteger)stackbufLength
{
return [self.children countByEnumeratingWithState:state objects:stackbuf count:stackbufLength];
}
ASEnvironmentLayoutOptionsForwarding
ASEnvironmentLayoutExtensibilityForwarding

View File

@@ -289,7 +289,8 @@ ASVisibilityDepthImplementation;
self.node.environmentState = environmentState;
[self.node setNeedsLayout];
for (id<ASEnvironment> child in self.node) {
NSArray<id<ASEnvironment>> *children = [self.node children];
for (id<ASEnvironment> child in children) {
ASEnvironmentStatePropagateDown(child, environmentState.environmentTraitCollection);
}
}

View File

@@ -99,7 +99,7 @@ ASDISPLAYNODE_EXTERN_C_END
* defined in an ASEnvironmentState up and down the ASEnvironment tree. To be able to define how merges of
* States should happen, specific merge functions can be provided
*/
@protocol ASEnvironment <NSObject, NSFastEnumeration>
@protocol ASEnvironment <NSObject>
/// The environment collection of an object which class conforms to the ASEnvironment protocol
- (ASEnvironmentState)environmentState;
@@ -126,7 +126,6 @@ ASDISPLAYNODE_EXTERN_C_END
/// sets a trait collection on this environment state.
- (void)setEnvironmentTraitCollection:(ASEnvironmentTraitCollection)environmentTraitCollection;
@end
// ASCollection/TableNodes don't actually have ASCellNodes as subnodes. Because of this we can't rely on display trait

View File

@@ -8,7 +8,7 @@
// of patent rights can be found in the PATENTS file in the same directory.
//
#import "ASLayoutSpec+Private.h"
#import "ASLayoutSpec.h"
#import "ASAssert.h"
#import "ASEnvironmentInternal.h"
@@ -17,13 +17,16 @@
#import "ASThread.h"
#import "ASTraitCollection.h"
#import <objc/runtime.h>
#import <map>
#import <vector>
typedef std::map<unsigned long, id<ASLayoutable>, std::less<unsigned long>> ASChildMap;
@interface ASLayoutSpec() {
ASEnvironmentState _environmentState;
ASDN::RecursiveMutex __instanceLock__;
ASChildrenMap _childrenMap;
unsigned long _mutations;
ASChildMap _children;
}
@end
@@ -32,7 +35,6 @@
// these dynamic properties all defined in ASLayoutOptionsPrivate.m
@dynamic spacingAfter, spacingBefore, flexGrow, flexShrink, flexBasis,
alignSelf, ascender, descender, sizeRange, layoutPosition, layoutableType;
@synthesize parent = _parent;
@synthesize isFinalLayoutable = _isFinalLayoutable;
- (instancetype)init
@@ -42,7 +44,6 @@
}
_isMutable = YES;
_environmentState = ASEnvironmentStateMakeDefault();
_mutations = 0;
return self;
}
@@ -104,8 +105,6 @@
return child;
}
#pragma mark - Parent
- (void)setParent:(id<ASLayoutable>)parent
{
// FIXME: Locking should be evaluated here. _parent is not widely used yet, though.
@@ -116,16 +115,18 @@
}
}
- (id<ASLayoutable>)parent
{
return _parent;
}
#pragma mark - Children
- (void)setChild:(id<ASLayoutable>)child
{
[self setChild:child forIndex:0];
ASDisplayNodeAssert(self.isMutable, @"Cannot set properties when layout spec is not mutable");
if (child) {
id<ASLayoutable> finalLayoutable = [self layoutableToAddFromLayoutable:child];
if (finalLayoutable) {
_children[0] = finalLayoutable;
[self propagateUpLayoutable:finalLayoutable];
}
} else {
_children.erase(0);
}
}
- (void)setChild:(id<ASLayoutable>)child forIndex:(NSUInteger)index
@@ -133,16 +134,11 @@
ASDisplayNodeAssert(self.isMutable, @"Cannot set properties when layout spec is not mutable");
if (child) {
id<ASLayoutable> finalLayoutable = [self layoutableToAddFromLayoutable:child];
if (finalLayoutable) {
_childrenMap[index] = finalLayoutable;
[self propagateUpLayoutable:finalLayoutable];
}
_children[index] = finalLayoutable;
} else {
_childrenMap.erase(index);
_children.erase(index);
}
_mutations++;
// TODO: Should we propagate up the layoutable as it could happen that multiple children will propagated up their
// TODO: Should we propagate up the layoutable at it could happen that multiple children will propagated up their
// layout options and one child will overwrite values from another child
// [self propagateUpLayoutable:finalLayoutable];
}
@@ -151,73 +147,37 @@
{
ASDisplayNodeAssert(self.isMutable, @"Cannot set properties when layout spec is not mutable");
_childrenMap.clear();
_children.clear();
NSUInteger i = 0;
for (id<ASLayoutable> child in children) {
_childrenMap[i] = [self layoutableToAddFromLayoutable:child];
_children[i] = [self layoutableToAddFromLayoutable:child];
i += 1;
_mutations++;
}
}
- (id<ASLayoutable>)childForIndex:(NSUInteger)index
{
if (index < _childrenMap.size()) {
return _childrenMap[index];
if (index < _children.size()) {
return _children[index];
}
return nil;
}
- (id<ASLayoutable>)child
{
return _childrenMap[0];
return _children[0];
}
- (NSArray *)children
{
// If used inside ASDK, the childrenMap property should be preferred over the children array to prevent
// unecessary boxing
std::vector<ASLayout *> children;
for (auto const &entry : _childrenMap) {
children.push_back(entry.second);
for (ASChildMap::iterator it = _children.begin(); it != _children.end(); ++it ) {
children.push_back(it->second);
}
return [NSArray arrayWithObjects:&children[0] count:children.size()];
}
#pragma mark - NSFastEnumeration
- (NSUInteger)countByEnumeratingWithState:(NSFastEnumerationState *)state
objects:(id __unsafe_unretained [])stackbuf
count:(NSUInteger)stackbufLength
{
NSUInteger count = 0;
unsigned long countOfItemsAlreadyEnumerated = state->state;
if (countOfItemsAlreadyEnumerated == 0) {
state->mutationsPtr = &_mutations;
}
if (countOfItemsAlreadyEnumerated < _childrenMap.size()) {
state->itemsPtr = stackbuf;
while((countOfItemsAlreadyEnumerated < _childrenMap.size()) && (count < stackbufLength)) {
// Hold on for the object while enumerating
__autoreleasing id child = _childrenMap[countOfItemsAlreadyEnumerated];
stackbuf[count] = child;
countOfItemsAlreadyEnumerated++;
count++;
}
} else {
count = 0;
}
state->state = countOfItemsAlreadyEnumerated;
return count;
}
#pragma mark - ASEnvironment
- (ASEnvironmentState)environmentState
@@ -273,15 +233,6 @@ ASEnvironmentLayoutExtensibilityForwarding
@end
@implementation ASLayoutSpec (Private)
- (ASChildrenMap)childrenMap
{
return _childrenMap;
}
@end
@implementation ASLayoutSpec (Debugging)
#pragma mark - ASLayoutableAsciiArtProtocol

View File

@@ -13,7 +13,6 @@
#import "ASInternalHelpers.h"
#import "ASLayoutSpec+Private.h"
#import "ASLayoutSpecUtilities.h"
#import "ASStackBaselinePositionedLayout.h"
#import "ASThread.h"
@@ -59,7 +58,7 @@
_alignItems = alignItems;
_justifyContent = justifyContent;
self.children = children;
[self setChildren:children];
return self;
}
@@ -121,9 +120,7 @@
- (ASLayout *)measureWithSizeRange:(ASSizeRange)constrainedSize
{
auto const &children = self.childrenMap;
if (children.size() == 0) {
if (self.children.count == 0) {
return [ASLayout layoutWithLayoutableObject:self
constrainedSizeRange:constrainedSize
size:constrainedSize.min];
@@ -132,9 +129,9 @@
ASStackLayoutSpecStyle style = {.direction = _direction, .spacing = _spacing, .justifyContent = _justifyContent, .alignItems = _alignItems, .baselineRelativeArrangement = _baselineRelativeArrangement};
BOOL needsBaselinePass = _baselineRelativeArrangement || _alignItems == ASStackLayoutAlignItemsBaselineFirst || _alignItems == ASStackLayoutAlignItemsBaselineLast;
std::vector<id<ASLayoutable>> stackChildren;
for (auto const &entry : children) {
stackChildren.push_back(entry.second);
std::vector<id<ASLayoutable>> stackChildren = std::vector<id<ASLayoutable>>();
for (id<ASLayoutable> child in self.children) {
stackChildren.push_back(child);
}
const auto unpositionedLayout = ASStackUnpositionedLayout::compute(stackChildren, style, constrainedSize);
@@ -146,19 +143,15 @@
// regardless of whether or not this stack aligns to baseline, we should let ASStackBaselinePositionedLayout::compute find the max ascender
// and min descender in case this spec is a child in another spec that wants to align to a baseline.
const auto baselinePositionedLayout = ASStackBaselinePositionedLayout::compute(positionedLayout, style, constrainedSize);
{
ASDN::MutexLocker l(__instanceLock__);
if (self.direction == ASStackLayoutDirectionVertical) {
if (stackChildren.size() > 0) {
self.ascender = stackChildren.front().ascender;
self.descender = stackChildren.back().descender;
}
ASDN::MutexLocker l(__instanceLock__);
self.ascender = [[self.children firstObject] ascender];
self.descender = [[self.children lastObject] descender];
} else {
ASDN::MutexLocker l(__instanceLock__);
self.ascender = baselinePositionedLayout.ascender;
self.descender = baselinePositionedLayout.descender;
}
}
if (needsBaselinePass) {
finalSize = directionSize(style.direction, unpositionedLayout.stackDimensionSum, baselinePositionedLayout.crossSize);

View File

@@ -10,7 +10,6 @@
#import "ASStaticLayoutSpec.h"
#import "ASLayoutSpec+Private.h"
#import "ASLayoutSpecUtilities.h"
#import "ASLayout.h"
@@ -39,8 +38,10 @@
{
CGSize maxConstrainedSize = CGSizeMake(constrainedSize.max.width, constrainedSize.max.height);
NSMutableArray *sublayouts = [NSMutableArray arrayWithCapacity:self.childrenMap.size()];
for (id<ASLayoutable> child in self) {
NSArray *children = self.children;
NSMutableArray *sublayouts = [NSMutableArray arrayWithCapacity:children.count];
for (id<ASLayoutable> child in children) {
CGPoint layoutPosition = child.layoutPosition;
CGSize autoMaxSize = CGSizeMake(maxConstrainedSize.width - layoutPosition.x,
maxConstrainedSize.height - layoutPosition.y);

View File

@@ -44,7 +44,7 @@ void ASEnvironmentPerformBlockOnObjectAndChildren(id<ASEnvironment> object, void
block(object);
for (id<ASEnvironment> child in object) {
for (id<ASEnvironment> child in [object children]) {
queue.push(child);
}
}

View File

@@ -1,25 +0,0 @@
//
// ASLayoutSpec+Private.h
// AsyncDisplayKit
//
// Copyright (c) 2014-present, Facebook, Inc. All rights reserved.
// This source code is licensed under the BSD-style license found in the
// LICENSE file in the root directory of this source tree. An additional grant
// of patent rights can be found in the PATENTS file in the same directory.
//
#import "ASLayoutSpec.h"
#import <objc/runtime.h>
#import <map>
typedef std::map<unsigned long, id<ASLayoutable>, std::less<unsigned long>> ASChildrenMap;
@interface ASLayoutSpec (Private)
/*
* Inside ASDK the childrenMap property should be preferred over the children array to prevent unecessary boxing
*/
@property (nonatomic, assign, readonly) ASChildrenMap childrenMap;
@end

View File

@@ -1723,24 +1723,6 @@ static inline BOOL _CGPointEqualToPointWithEpsilon(CGPoint point1, CGPoint point
XCTAssertEqual(1, view.subviews.count, @"View should have 1 subview");
}
- (void)testFastEnumeration
{
ASDisplayNode *parent = [[ASDisplayNode alloc] init];
NSMutableArray *children = [NSMutableArray array];
for (int i = 0; i < 100; i++) {
ASDisplayNode *child = [[[ASDisplayNode alloc] init] autorelease];
[children addObject:child];
[parent addSubnode:child];
}
NSInteger i = 0;
for (ASDisplayNode *child in parent) {
XCTAssertEqualObjects(child, children[i]);
i++;
}
}
- (void)checkBackgroundColorOpaqueRelationshipWithViewLoaded:(BOOL)loaded layerBacked:(BOOL)isLayerBacked
{
ASDisplayNode *node = [[ASDisplayNode alloc] init];

View File

@@ -42,23 +42,6 @@
ASSnapshotVerifyNode(node, identifier);
}
- (void)testFastEnumeration
{
ASLayoutSpec *layoutSpec = [[ASLayoutSpec alloc] init];
NSMutableArray *children = [NSMutableArray array];
for (int i = 0; i < 100; i++) {
[children addObject:[[ASDisplayNode alloc] init]];
}
layoutSpec.children = children;
NSInteger i = 0;
for (ASDisplayNode *child in layoutSpec) {
XCTAssertEqualObjects(child, children[i]);
i++;
}
}
@end
@implementation ASTestNode