From f33f84e75f1957f381e34bc99a902b9c324db6fa Mon Sep 17 00:00:00 2001 From: Valentin Shergin Date: Wed, 1 Feb 2017 12:59:26 -0800 Subject: [PATCH] Deprecating/removing `setFrame`, `setLeftTop`, and co. Summary: Motivation: * `RCTShadowView`'s `frame` property actually represents computed layout of the view. We must not use it as a setter for yoga node styles; * Using `frame` and `setLeftTop` in existing way actually works only for view with absolute positioning, so it is super rare and special case; * Internally, setting `frame` only make sense to `RootView`, and in that case there we always must not change `origin` we are introducing `setSize` method. Changes: * `[-RCTShadowView setFrame:]` was removed, `frame` property is readonly now; * `[-RCTShadowView setLeftTop:]` was removed; no replacement provided; * `[-RCTShadowView size]` read-write property was added; * `[-RCTUIManager setFrame:forView:]` was deprecated, use (just introduced) `setSize:forView:` instead; * `[-RCTUIManager setSize:forView:]` was added. If you are still need some of removed methods, you are probably doing something wrong. Consider using `setIntrinsicContentSize`-family methods, `setSize`-family methods, or (in the worst case) accessing `yogaNode` directly. Reviewed By: javache Differential Revision: D4491384 fbshipit-source-id: 56dd84567324c5a86e4c870a41c38322dc1224d2 --- React/Modules/RCTUIManager.h | 16 +++++++++-- React/Modules/RCTUIManager.m | 20 ++++++++++---- React/Views/RCTModalHostViewManager.m | 3 +-- React/Views/RCTShadowView.h | 23 +++++++++------- React/Views/RCTShadowView.m | 38 +++++++++++++-------------- 5 files changed, 62 insertions(+), 38 deletions(-) diff --git a/React/Modules/RCTUIManager.h b/React/Modules/RCTUIManager.h index 421bea883..0acabc6d6 100644 --- a/React/Modules/RCTUIManager.h +++ b/React/Modules/RCTUIManager.h @@ -71,10 +71,10 @@ RCT_EXTERN NSString *const RCTUIManagerRootViewKey; - (UIView *)viewForReactTag:(NSNumber *)reactTag; /** - * Update the frame of a view. This might be in response to a screen rotation + * Set the size of a view. This might be in response to a screen rotation * or some other layout event outside of the React-managed view hierarchy. */ -- (void)setFrame:(CGRect)frame forView:(UIView *)view; +- (void)setSize:(CGSize)size forView:(UIView *)view; /** * Set the natural size of a view, which is used when no explicit size is set. @@ -139,6 +139,18 @@ RCT_EXTERN NSString *const RCTUIManagerRootViewKey; @end +@interface RCTUIManager (Deprecated) + +/** + * This method is deprecated and will be removed in next releases. + * Use `setSize:forView:` or `setIntrinsicContentSize:forView:` instead. + * Only frames with `origin` equals {0, 0} are supported. + */ +- (void)setFrame:(CGRect)frame forView:(UIView *)view +__deprecated_msg("Use `setSize:forView:` or `setIntrinsicContentSize:forView:` instead."); + +@end + /** * This category makes the current RCTUIManager instance available via the * RCTBridge, which is useful for RCTBridgeModules or RCTViewManagers that diff --git a/React/Modules/RCTUIManager.m b/React/Modules/RCTUIManager.m index acde98a24..b72323589 100644 --- a/React/Modules/RCTUIManager.m +++ b/React/Modules/RCTUIManager.m @@ -390,7 +390,7 @@ dispatch_queue_t RCTGetUIManagerQueue(void) // Register view _viewRegistry[reactTag] = rootView; - CGRect frame = rootView.frame; + CGSize size = rootView.bounds.size; // Register shadow view dispatch_async(RCTGetUIManagerQueue(), ^{ @@ -400,7 +400,7 @@ dispatch_queue_t RCTGetUIManagerQueue(void) RCTRootShadowView *shadowView = [RCTRootShadowView new]; shadowView.reactTag = reactTag; - shadowView.frame = frame; + shadowView.size = size; shadowView.backgroundColor = rootView.backgroundColor; shadowView.viewName = NSStringFromClass([rootView class]); shadowView.sizeFlexibility = sizeFlexibility; @@ -425,7 +425,7 @@ dispatch_queue_t RCTGetUIManagerQueue(void) return _viewRegistry[reactTag]; } -- (void)setFrame:(CGRect)frame forView:(UIView *)view +- (void)setSize:(CGSize)size forView:(UIView *)view { RCTAssertMainQueue(); @@ -445,8 +445,8 @@ dispatch_queue_t RCTGetUIManagerQueue(void) RCTAssert(shadowView != nil, @"Could not locate shadow view with tag #%@", reactTag); BOOL needsLayout = NO; - if (!CGRectEqualToRect(frame, shadowView.frame)) { - shadowView.frame = frame; + if (!CGSizeEqualToSize(size, shadowView.size)) { + shadowView.size = size; needsLayout = YES; } @@ -1643,6 +1643,16 @@ static UIView *_jsResponder; @end +@implementation RCTUIManager (Deprecated) + +- (void)setFrame:(CGRect)frame forView:(UIView *)view +{ + RCTLogWarn(@"Calling of `[-RCTUIManager setFrame:forView:]` which is deprecated."); + [self setSize:frame.size forView:view]; +} + +@end + @implementation RCTBridge (RCTUIManager) - (RCTUIManager *)uiManager diff --git a/React/Views/RCTModalHostViewManager.m b/React/Views/RCTModalHostViewManager.m index 8f99b5c73..31821af33 100644 --- a/React/Views/RCTModalHostViewManager.m +++ b/React/Views/RCTModalHostViewManager.m @@ -25,8 +25,7 @@ { [super insertReactSubview:subview atIndex:atIndex]; if ([subview isKindOfClass:[RCTShadowView class]]) { - CGRect frame = {.origin = CGPointZero, .size = RCTScreenSize()}; - [(RCTShadowView *)subview setFrame:frame]; + ((RCTShadowView *)subview).size = RCTScreenSize(); } } diff --git a/React/Views/RCTShadowView.h b/React/Views/RCTShadowView.h index 1944bc55a..92c1b56dc 100644 --- a/React/Views/RCTShadowView.h +++ b/React/Views/RCTShadowView.h @@ -79,17 +79,11 @@ typedef void (^RCTApplierBlock)(NSDictionary *viewRegistry @property (nonatomic, assign) YGValue minHeight; @property (nonatomic, assign) YGValue maxHeight; -@property (nonatomic, assign) CGRect frame; - /** - * Represents the natural size of the view, which is used when explicit size is not set or is ambiguous. - * Defaults to `{UIViewNoIntrinsicMetric, UIViewNoIntrinsicMetric}`. + * Convenient alias to `width` and `height` in pixels. + * Defaults to NAN in case of non-pixel dimention. */ -@property (nonatomic, assign) CGSize intrinsicContentSize; - - -- (void)setTopLeft:(CGPoint)topLeft; -- (void)setSize:(CGSize)size; +@property (nonatomic, assign) CGSize size; /** * Border. Defaults to { 0, 0, 0, 0 }. @@ -152,6 +146,17 @@ typedef void (^RCTApplierBlock)(NSDictionary *viewRegistry */ @property (nonatomic, assign) YGOverflow overflow; +/** + * Computed position of the view. + */ +@property (nonatomic, assign, readonly) CGRect frame; + +/** + * Represents the natural size of the view, which is used when explicit size is not set or is ambiguous. + * Defaults to `{UIViewNoIntrinsicMetric, UIViewNoIntrinsicMetric}`. + */ +@property (nonatomic, assign) CGSize intrinsicContentSize; + /** * Calculate property changes that need to be propagated to the view. * The applierBlocks set contains RCTApplierBlock functions that must be applied diff --git a/React/Views/RCTShadowView.m b/React/Views/RCTShadowView.m index 5f8140c37..e46e2b306 100644 --- a/React/Views/RCTShadowView.m +++ b/React/Views/RCTShadowView.m @@ -547,17 +547,27 @@ RCT_POSITION_PROPERTY(Right, right, YGEdgeEnd) RCT_POSITION_PROPERTY(Bottom, bottom, YGEdgeBottom) RCT_POSITION_PROPERTY(Left, left, YGEdgeStart) -- (void)setFrame:(CGRect)frame +// Size + +- (CGSize)size { - if (!CGRectEqualToRect(frame, _frame)) { - _frame = frame; - YGNodeStyleSetPosition(_cssNode, YGEdgeLeft, CGRectGetMinX(frame)); - YGNodeStyleSetPosition(_cssNode, YGEdgeTop, CGRectGetMinY(frame)); - YGNodeStyleSetWidth(_cssNode, CGRectGetWidth(frame)); - YGNodeStyleSetHeight(_cssNode, CGRectGetHeight(frame)); - } + YGValue width = YGNodeStyleGetWidth(_cssNode); + YGValue height = YGNodeStyleGetHeight(_cssNode); + + return CGSizeMake( + width.unit == YGUnitPixel ? width.value : NAN, + height.unit == YGUnitPixel ? height.value : NAN + ); } +- (void)setSize:(CGSize)size +{ + YGNodeStyleSetWidth(_cssNode, size.width); + YGNodeStyleSetHeight(_cssNode, size.height); +} + +// IntrinsicContentSize + static inline YGSize RCTShadowViewMeasure(YGNodeRef node, float width, YGMeasureMode widthMode, float height, YGMeasureMode heightMode) { RCTShadowView *shadowView = (__bridge RCTShadowView *)YGNodeGetContext(node); @@ -613,18 +623,6 @@ static inline YGSize RCTShadowViewMeasure(YGNodeRef node, float width, YGMeasure YGNodeMarkDirty(_cssNode); } -- (void)setTopLeft:(CGPoint)topLeft -{ - YGNodeStyleSetPosition(_cssNode, YGEdgeLeft, topLeft.x); - YGNodeStyleSetPosition(_cssNode, YGEdgeTop, topLeft.y); -} - -- (void)setSize:(CGSize)size -{ - YGNodeStyleSetWidth(_cssNode, size.width); - YGNodeStyleSetHeight(_cssNode, size.height); -} - // Flex - (void)setFlex:(float)value