From 2091df9607f3c95b99be46396dc460fedee57907 Mon Sep 17 00:00:00 2001 From: Nikita Lutsenko Date: Tue, 16 Aug 2016 10:18:51 -0700 Subject: [PATCH] [ASTextNode] Fix highlighting when textContainerInsets are set. (#2073) * [ASTextNode] Fix highlighting when textContainerInsets are set. * Add ASTextNodeSnapshotTests to xcodeproj. * Add snapshot test for container inset and highlighting. --- AsyncDisplayKit.xcodeproj/project.pbxproj | 4 ++++ AsyncDisplayKit/ASTextNode.mm | 7 ++++++ .../ASTextNodeSnapshotTests.m | 22 ++++++++++++++++++ .../testTextContainerInsetHighlight@2x.png | Bin 0 -> 4877 bytes 4 files changed, 33 insertions(+) create mode 100644 AsyncDisplayKitTests/ReferenceImages_64/ASTextNodeSnapshotTests/testTextContainerInsetHighlight@2x.png diff --git a/AsyncDisplayKit.xcodeproj/project.pbxproj b/AsyncDisplayKit.xcodeproj/project.pbxproj index 9cf13a4e4b..20082d807f 100644 --- a/AsyncDisplayKit.xcodeproj/project.pbxproj +++ b/AsyncDisplayKit.xcodeproj/project.pbxproj @@ -225,6 +225,7 @@ 8021EC1D1D2B00B100799119 /* UIImage+ASConvenience.h in Headers */ = {isa = PBXBuildFile; fileRef = 8021EC1A1D2B00B100799119 /* UIImage+ASConvenience.h */; settings = {ATTRIBUTES = (Public, ); }; }; 8021EC1E1D2B00B100799119 /* UIImage+ASConvenience.m in Sources */ = {isa = PBXBuildFile; fileRef = 8021EC1B1D2B00B100799119 /* UIImage+ASConvenience.m */; }; 8021EC1F1D2B00B100799119 /* UIImage+ASConvenience.m in Sources */ = {isa = PBXBuildFile; fileRef = 8021EC1B1D2B00B100799119 /* UIImage+ASConvenience.m */; }; + 81E95C141D62639600336598 /* ASTextNodeSnapshotTests.m in Sources */ = {isa = PBXBuildFile; fileRef = 81E95C131D62639600336598 /* ASTextNodeSnapshotTests.m */; }; 81EE38501C8E94F000456208 /* ASRunLoopQueue.mm in Sources */ = {isa = PBXBuildFile; fileRef = 81EE384E1C8E94F000456208 /* ASRunLoopQueue.mm */; }; 83A7D95A1D44542100BF333E /* ASWeakMap.m in Sources */ = {isa = PBXBuildFile; fileRef = 83A7D9591D44542100BF333E /* ASWeakMap.m */; }; 83A7D95B1D44547700BF333E /* ASWeakMap.m in Sources */ = {isa = PBXBuildFile; fileRef = 83A7D9591D44542100BF333E /* ASWeakMap.m */; }; @@ -977,6 +978,7 @@ 7AB338681C55B97B0055FDE8 /* ASRelativeLayoutSpecSnapshotTests.mm */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.objcpp; path = ASRelativeLayoutSpecSnapshotTests.mm; sourceTree = ""; }; 8021EC1A1D2B00B100799119 /* UIImage+ASConvenience.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = "UIImage+ASConvenience.h"; sourceTree = ""; }; 8021EC1B1D2B00B100799119 /* UIImage+ASConvenience.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = "UIImage+ASConvenience.m"; sourceTree = ""; }; + 81E95C131D62639600336598 /* ASTextNodeSnapshotTests.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = ASTextNodeSnapshotTests.m; sourceTree = ""; }; 81EE384D1C8E94F000456208 /* ASRunLoopQueue.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; name = ASRunLoopQueue.h; path = ../ASRunLoopQueue.h; sourceTree = ""; }; 81EE384E1C8E94F000456208 /* ASRunLoopQueue.mm */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.objcpp; name = ASRunLoopQueue.mm; path = ../ASRunLoopQueue.mm; sourceTree = ""; }; 83A7D9581D44542100BF333E /* ASWeakMap.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = ASWeakMap.h; sourceTree = ""; }; @@ -1336,6 +1338,7 @@ ACF6ED5A1B178DC700DA7C62 /* ASRatioLayoutSpecSnapshotTests.mm */, ACF6ED5B1B178DC700DA7C62 /* ASStackLayoutSpecSnapshotTests.mm */, AC026B571BD3F61800BBC17E /* ASStaticLayoutSpecSnapshotTests.m */, + 81E95C131D62639600336598 /* ASTextNodeSnapshotTests.m */, ACF6ED571B178DC700DA7C62 /* ASLayoutSpecSnapshotTestsHelper.h */, ACF6ED581B178DC700DA7C62 /* ASLayoutSpecSnapshotTestsHelper.m */, 242995D21B29743C00090100 /* ASBasicImageDownloaderTests.m */, @@ -2195,6 +2198,7 @@ 254C6B541BF8FF2A003EC431 /* ASTextKitTests.mm in Sources */, 05EA6FE71AC0966E00E35788 /* ASSnapshotTestCase.mm in Sources */, ACF6ED631B178DC700DA7C62 /* ASStackLayoutSpecSnapshotTests.mm in Sources */, + 81E95C141D62639600336598 /* ASTextNodeSnapshotTests.m in Sources */, 3C9C128519E616EF00E942A0 /* ASTableViewTests.m in Sources */, AEEC47E41C21D3D200EC1693 /* ASVideoNodeTests.m in Sources */, 254C6B521BF8FE6D003EC431 /* ASTextKitTruncationTests.mm in Sources */, diff --git a/AsyncDisplayKit/ASTextNode.mm b/AsyncDisplayKit/ASTextNode.mm index b658be8a4e..2517eefaab 100644 --- a/AsyncDisplayKit/ASTextNode.mm +++ b/AsyncDisplayKit/ASTextNode.mm @@ -781,6 +781,13 @@ static NSArray *DefaultLinkAttributeNames = @[ NSLinkAttributeName ]; for (NSValue *rectValue in highlightRects) { UIEdgeInsets shadowPadding = _renderer.shadower.shadowPadding; CGRect rendererRect = ASTextNodeAdjustRenderRectForShadowPadding(rectValue.CGRectValue, shadowPadding); + + // The rects returned from renderer don't have `textContainerInset`, + // as well as they are using the `constrainedSize` for layout, + // so we can simply increase the rect by insets to get the full blown layout. + rendererRect.size.width += _textContainerInset.left + _textContainerInset.right; + rendererRect.size.height += _textContainerInset.top + _textContainerInset.bottom; + CGRect highlightedRect = [self.layer convertRect:rendererRect toLayer:highlightTargetLayer]; // We set our overlay layer's frame to the bounds of the highlight target layer. diff --git a/AsyncDisplayKitTests/ASTextNodeSnapshotTests.m b/AsyncDisplayKitTests/ASTextNodeSnapshotTests.m index 78b420bfc5..a52a8c7509 100644 --- a/AsyncDisplayKitTests/ASTextNodeSnapshotTests.m +++ b/AsyncDisplayKitTests/ASTextNodeSnapshotTests.m @@ -32,4 +32,26 @@ ASSnapshotVerifyNode(textNode, nil); } +- (void)testTextContainerInsetHighlight +{ + UIView *backgroundView = [[UIView alloc] initWithFrame:CGRectZero]; + backgroundView.layer.as_allowsHighlightDrawing = YES; + + ASTextNode *textNode = [[ASTextNode alloc] init]; + textNode.attributedText = [[NSAttributedString alloc] initWithString:@"yolo" + attributes:@{ NSFontAttributeName : [UIFont systemFontOfSize:30] }]; + + [textNode measureWithSizeRange:ASSizeRangeMake(CGSizeZero, CGSizeMake(CGFLOAT_MAX, CGFLOAT_MAX))]; + textNode.frame = CGRectMake(50, 50, textNode.calculatedSize.width, textNode.calculatedSize.height); + textNode.textContainerInset = UIEdgeInsetsMake(5, 10, 10, 5); + + [backgroundView addSubview:textNode.view]; + backgroundView.frame = UIEdgeInsetsInsetRect(textNode.bounds, UIEdgeInsetsMake(-50, -50, -50, -50)); + + textNode.highlightRange = NSMakeRange(0, textNode.attributedText.length); + + [ASSnapshotTestCase hackilySynchronouslyRecursivelyRenderNode:textNode]; + FBSnapshotVerifyLayer(backgroundView.layer, nil); +} + @end diff --git a/AsyncDisplayKitTests/ReferenceImages_64/ASTextNodeSnapshotTests/testTextContainerInsetHighlight@2x.png b/AsyncDisplayKitTests/ReferenceImages_64/ASTextNodeSnapshotTests/testTextContainerInsetHighlight@2x.png new file mode 100644 index 0000000000000000000000000000000000000000..4a2fa33448404b42eb3f35c85d2b6ff8845c8e1b GIT binary patch literal 4877 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 literal 0 HcmV?d00001