Skip to content

Commit a95dd17

Browse files
committed
add FeedItemTextureView
1 parent fbba0a6 commit a95dd17

File tree

4 files changed

+295
-0
lines changed

4 files changed

+295
-0
lines changed

LayoutFrameworkBenchmark.xcodeproj/project.pbxproj

+12
Original file line numberDiff line numberDiff line change
@@ -26,6 +26,7 @@
2626
24661D0A1F4EFFF5002CB883 /* LaunchScreen.storyboard in Resources */ = {isa = PBXBuildFile; fileRef = 24661D081F4EFFF5002CB883 /* LaunchScreen.storyboard */; };
2727
639E5A2020DF62D700C6BCEA /* NKFrameLayoutKitView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 639E5A1F20DF62D700C6BCEA /* NKFrameLayoutKitView.swift */; };
2828
BF3DC69820B560A400536177 /* FeedItemNotAutoLayoutView.swift in Sources */ = {isa = PBXBuildFile; fileRef = BF3DC69720B560A400536177 /* FeedItemNotAutoLayoutView.swift */; };
29+
E4A8A14124FE99B1009D872B /* FeedItemTextureView.swift in Sources */ = {isa = PBXBuildFile; fileRef = E4A8A14024FE982E009D872B /* FeedItemTextureView.swift */; };
2930
/* End PBXBuildFile section */
3031

3132
/* Begin PBXFileReference section */
@@ -52,6 +53,7 @@
5253
639E5A1F20DF62D700C6BCEA /* NKFrameLayoutKitView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = NKFrameLayoutKitView.swift; sourceTree = "<group>"; };
5354
73BD901DE3512A23A7603899 /* Pods-LayoutFrameworkBenchmark.debug.xcconfig */ = {isa = PBXFileReference; includeInIndex = 1; lastKnownFileType = text.xcconfig; name = "Pods-LayoutFrameworkBenchmark.debug.xcconfig"; path = "Pods/Target Support Files/Pods-LayoutFrameworkBenchmark/Pods-LayoutFrameworkBenchmark.debug.xcconfig"; sourceTree = "<group>"; };
5455
BF3DC69720B560A400536177 /* FeedItemNotAutoLayoutView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = FeedItemNotAutoLayoutView.swift; sourceTree = "<group>"; };
56+
E4A8A14024FE982E009D872B /* FeedItemTextureView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = FeedItemTextureView.swift; sourceTree = "<group>"; };
5557
/* End PBXFileReference section */
5658

5759
/* Begin PBXFrameworksBuildPhase section */
@@ -69,6 +71,7 @@
6971
2401BC741F4F017D00788998 /* Benchmarks */ = {
7072
isa = PBXGroup;
7173
children = (
74+
E4A8A13F24FE981F009D872B /* Texture */,
7275
2401BCA21F4F045600788998 /* AutoLayout */,
7376
2401BC921F4F020D00788998 /* FlexLayout */,
7477
2401BC8D1F4F01CC00788998 /* LayoutKit */,
@@ -208,6 +211,14 @@
208211
name = NotAutoLayout;
209212
sourceTree = "<group>";
210213
};
214+
E4A8A13F24FE981F009D872B /* Texture */ = {
215+
isa = PBXGroup;
216+
children = (
217+
E4A8A14024FE982E009D872B /* FeedItemTextureView.swift */,
218+
);
219+
name = Texture;
220+
sourceTree = "<group>";
221+
};
211222
/* End PBXGroup section */
212223

213224
/* Begin PBXNativeTarget section */
@@ -348,6 +359,7 @@
348359
2401BC821F4F018C00788998 /* CollectionViewController.swift in Sources */,
349360
2401BC9E1F4F042700788998 /* FeedItemManualView.swift in Sources */,
350361
2401BC811F4F018C00788998 /* BenchmarkViewController.swift in Sources */,
362+
E4A8A14124FE99B1009D872B /* FeedItemTextureView.swift in Sources */,
351363
BF3DC69820B560A400536177 /* FeedItemNotAutoLayoutView.swift in Sources */,
352364
639E5A2020DF62D700C6BCEA /* NKFrameLayoutKitView.swift in Sources */,
353365
2401BC9B1F4F03B300788998 /* ProfileCardLayout.swift in Sources */,

LayoutFrameworkBenchmark/Benchmarks/BenchmarkViewController.swift

+5
Original file line numberDiff line numberDiff line change
@@ -18,6 +18,11 @@ class BenchmarkViewController: UITableViewController {
1818
//
1919
// Ordered alphabetically
2020
//
21+
22+
ViewControllerData(title: "Texture", factoryBlock: { viewCount in
23+
let data = FeedItemData.generate(count: viewCount)
24+
return CollectionViewControllerFeedItemTextureView(data: data)
25+
}),
2126

2227
ViewControllerData(title: "Auto Layout", factoryBlock: { viewCount in
2328
let data = FeedItemData.generate(count: viewCount)

LayoutFrameworkBenchmark/Benchmarks/CollectionViewController.swift

+1
Original file line numberDiff line numberDiff line change
@@ -22,6 +22,7 @@ import UIKit
2222
@available(iOS 9, *)
2323
class CollectionViewControllerFeedItemUIStackView: CollectionViewController<FeedItemUIStackView> {}
2424

25+
class CollectionViewControllerFeedItemTextureView: CollectionViewController<FeedItemTextureView> {}
2526
class CollectionViewControllerFeedItemAutoLayoutView: CollectionViewController<FeedItemAutoLayoutView> {}
2627
class CollectionViewControllerFeedItemLayoutKitView: CollectionViewController<FeedItemLayoutKitView> {}
2728
class CollectionViewControllerFeedItemManualView: CollectionViewController<FeedItemManualView> {}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,277 @@
1+
// Copyright 2016 LinkedIn Corp.
2+
// Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except in compliance with the License.
3+
// You may obtain a copy of the License at http://www.apache.org/licenses/LICENSE-2.0
4+
//
5+
// Unless required by applicable law or agreed to in writing,
6+
// software distributed under the License is distributed on an "AS IS" BASIS,
7+
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
8+
9+
import UIKit
10+
import AsyncDisplayKit
11+
12+
/// A LinkedIn feed item that is implemented with Texture.
13+
class FeedItemTextureView: UIView, DataBinder {
14+
15+
let topBarView = TopBarNode()
16+
let miniProfileView = MiniProfileNode()
17+
let miniContentView = MiniContentNode()
18+
let socialActionsView = SocialActionsNode()
19+
let commentView = CommentNode()
20+
21+
override init(frame: CGRect) {
22+
super.init(frame: frame)
23+
backgroundColor = UIColor.white
24+
let views: [String: UIView] = [
25+
"topBarView": topBarView,
26+
"miniProfileView": miniProfileView,
27+
"miniContentView": miniContentView,
28+
"socialActionsView": socialActionsView,
29+
"commentView": commentView
30+
]
31+
32+
addAutoLayoutSubviews(views)
33+
addConstraints(withVisualFormat: "V:|-0-[topBarView]-0-[miniProfileView]-0-[miniContentView]-0-[socialActionsView]-0-[commentView]-0-|", views: views)
34+
addConstraints(withVisualFormat: "H:|-0-[topBarView]-0-|", views: views)
35+
addConstraints(withVisualFormat: "H:|-0-[miniProfileView]-0-|", views: views)
36+
addConstraints(withVisualFormat: "H:|-0-[miniContentView]-0-|", views: views)
37+
addConstraints(withVisualFormat: "H:|-0-[socialActionsView]-0-|", views: views)
38+
addConstraints(withVisualFormat: "H:|-0-[commentView]-0-|", views: views)
39+
}
40+
41+
required init?(coder aDecoder: NSCoder) {
42+
fatalError("init(coder:) has not been implemented")
43+
}
44+
45+
func setData(_ data: FeedItemData) {
46+
topBarView.actionLabel.text = data.actionText
47+
miniProfileView.posterNameLabel.text = data.posterName
48+
miniProfileView.posterHeadlineLabel.text = data.posterHeadline
49+
miniProfileView.posterTimeLabel.text = data.posterTimestamp
50+
miniProfileView.posterCommentLabel.text = data.posterComment
51+
miniContentView.contentTitleLabel.text = data.contentTitle
52+
miniContentView.contentDomainLabel.text = data.contentDomain
53+
commentView.actorCommentLabel.text = data.actorComment
54+
}
55+
56+
override func sizeThatFits(_ size: CGSize) -> CGSize {
57+
return systemLayoutSizeFitting(CGSize(width: size.width, height: 0))
58+
}
59+
}
60+
61+
class CommentNode: UIView {
62+
let actorImageView: UIImageView = {
63+
let i = UIImageView()
64+
i.image = UIImage(named: "50x50.png")
65+
i.setContentHuggingPriority(UILayoutPriority.required, for: .horizontal)
66+
i.setContentCompressionResistancePriority(UILayoutPriority.required, for: .horizontal)
67+
return i
68+
}()
69+
70+
let actorCommentLabel: UILabel = UILabel()
71+
72+
init() {
73+
super.init(frame: .zero)
74+
75+
let views: [String: UIView] = [
76+
"actorImageView": actorImageView,
77+
"actorCommentLabel": actorCommentLabel
78+
]
79+
addAutoLayoutSubviews(views)
80+
81+
addConstraints(withVisualFormat: "H:|-0-[actorImageView]-0-[actorCommentLabel]-0-|", views: views)
82+
addConstraints(withVisualFormat: "V:|-0-[actorImageView]-(>=0)-|", views: views)
83+
addConstraints(withVisualFormat: "V:|-0-[actorCommentLabel]-(>=0)-|", views: views)
84+
addConstraints(withVisualFormat: "V:[actorImageView]-(0@749)-|", views: views)
85+
}
86+
87+
required init?(coder aDecoder: NSCoder) {
88+
fatalError("init(coder:) has not been implemented")
89+
}
90+
}
91+
92+
class MiniContentNode: UIView {
93+
let contentImageView: UIImageView = {
94+
let i = UIImageView()
95+
i.image = UIImage(named: "350x200.png")
96+
i.contentMode = .scaleAspectFit
97+
i.backgroundColor = UIColor.orange
98+
return i
99+
}()
100+
101+
let contentTitleLabel: UILabel = UILabel()
102+
let contentDomainLabel: UILabel = UILabel()
103+
104+
init() {
105+
super.init(frame: .zero)
106+
107+
let views: [String: UIView] = [
108+
"contentImageView": contentImageView,
109+
"contentTitleLabel": contentTitleLabel,
110+
"contentDomainLabel": contentDomainLabel
111+
]
112+
113+
addAutoLayoutSubviews(views)
114+
115+
addConstraints(withVisualFormat: "V:|-0-[contentImageView]-0-[contentTitleLabel]-0-[contentDomainLabel]-0-|", views: views)
116+
117+
addConstraints(withVisualFormat: "H:|-0-[contentImageView]-0-|", views: views)
118+
addConstraints(withVisualFormat: "H:|-0-[contentTitleLabel]-0-|", views: views)
119+
addConstraints(withVisualFormat: "H:|-0-[contentDomainLabel]-0-|", views: views)
120+
}
121+
122+
required init?(coder aDecoder: NSCoder) {
123+
fatalError("init(coder:) has not been implemented")
124+
}
125+
}
126+
127+
class MiniProfileNode: UIView {
128+
129+
let posterImageView: UIImageView = {
130+
let i = UIImageView()
131+
i.image = UIImage(named: "50x50.png")
132+
i.backgroundColor = UIColor.orange
133+
i.contentMode = .center
134+
i.setContentHuggingPriority(UILayoutPriority.required, for: .horizontal)
135+
i.setContentCompressionResistancePriority(UILayoutPriority.required, for: .horizontal)
136+
return i
137+
}()
138+
139+
let posterNameLabel: UILabel = {
140+
let l = UILabel()
141+
l.backgroundColor = UIColor.yellow
142+
return l
143+
}()
144+
145+
let posterHeadlineLabel: UILabel = {
146+
let l = UILabel()
147+
l.numberOfLines = 3
148+
l.backgroundColor = UIColor.yellow
149+
return l
150+
}()
151+
152+
let posterTimeLabel: UILabel = {
153+
let l = UILabel()
154+
l.backgroundColor = UIColor.yellow
155+
return l
156+
}()
157+
158+
let posterCommentLabel: UILabel = UILabel()
159+
160+
init() {
161+
super.init(frame: .zero)
162+
163+
let views: [String: UIView] = [
164+
"posterImageView": posterImageView,
165+
"posterNameLabel": posterNameLabel,
166+
"posterHeadlineLabel": posterHeadlineLabel,
167+
"posterTimeLabel": posterTimeLabel,
168+
"posterCommentLabel": posterCommentLabel
169+
]
170+
addAutoLayoutSubviews(views)
171+
addConstraints(withVisualFormat: "V:|-0-[posterImageView]-(>=0)-[posterCommentLabel]-0-|", views: views)
172+
addConstraints(withVisualFormat: "V:|-1-[posterNameLabel]-1-[posterHeadlineLabel]-1-[posterTimeLabel]-(>=3)-[posterCommentLabel]", views: views)
173+
addConstraints(withVisualFormat: "V:[posterImageView]-(0@749)-[posterCommentLabel]", views: views)
174+
175+
addConstraints(withVisualFormat: "H:|-0-[posterImageView]-2-[posterNameLabel]-4-|", views: views)
176+
addConstraints(withVisualFormat: "H:[posterImageView]-2-[posterHeadlineLabel]-4-|", views: views)
177+
addConstraints(withVisualFormat: "H:[posterImageView]-2-[posterTimeLabel]-4-|", views: views)
178+
addConstraints(withVisualFormat: "H:|-0-[posterCommentLabel]-0-|", views: views)
179+
}
180+
181+
required init?(coder aDecoder: NSCoder) {
182+
fatalError("init(coder:) has not been implemented")
183+
}
184+
}
185+
186+
class SocialActionsNode: UIView {
187+
let likeLabel: UILabel = {
188+
let l = UILabel()
189+
l.text = "Like"
190+
l.backgroundColor = .green
191+
return l
192+
}()
193+
194+
let commentLabel: UILabel = {
195+
let l = UILabel()
196+
l.text = "Comment"
197+
l.backgroundColor = .green
198+
l.textAlignment = .center
199+
return l
200+
}()
201+
202+
let shareLabel: UILabel = {
203+
let l = UILabel()
204+
l.text = "Share"
205+
l.textAlignment = .right
206+
l.backgroundColor = .green
207+
return l
208+
}()
209+
210+
init() {
211+
super.init(frame: .zero)
212+
213+
let views: [String: UIView] = [
214+
"likeLabel": likeLabel,
215+
"commentLabel": commentLabel,
216+
"shareLabel": shareLabel
217+
]
218+
addAutoLayoutSubviews(views)
219+
220+
addConstraints(withVisualFormat: "V:|-0-[likeLabel]-0-|", views: views)
221+
addConstraints(withVisualFormat: "V:|-0-[commentLabel]-0-|", views: views)
222+
addConstraints(withVisualFormat: "V:|-0-[shareLabel]-0-|", views: views)
223+
224+
addConstraints([
225+
NSLayoutConstraint(item: likeLabel, attribute: .leadingMargin, relatedBy: .equal, toItem: self, attribute: .leadingMargin, multiplier: 1, constant: 0),
226+
NSLayoutConstraint(item: commentLabel, attribute: .centerX, relatedBy: .equal, toItem: self, attribute: .centerX, multiplier: 1, constant: 0),
227+
NSLayoutConstraint(item: shareLabel, attribute: .trailingMargin, relatedBy: .equal, toItem: self, attribute: .trailingMargin, multiplier: 1, constant: 0)
228+
])
229+
}
230+
231+
required init?(coder aDecoder: NSCoder) {
232+
fatalError("init(coder:) has not been implemented")
233+
}
234+
}
235+
236+
class TopBarNode: UIView {
237+
let actionLabel: UILabel = UILabel()
238+
239+
let optionsLabel: UILabel = {
240+
let l = UILabel()
241+
l.text = "..."
242+
l.setContentHuggingPriority(UILayoutPriority.required, for: .horizontal)
243+
l.setContentCompressionResistancePriority(UILayoutPriority.required, for: .horizontal)
244+
return l
245+
}()
246+
247+
init() {
248+
super.init(frame: .zero)
249+
let views: [String: UIView] = ["actionLabel": actionLabel, "optionsLabel": optionsLabel]
250+
addAutoLayoutSubviews(views)
251+
addConstraints(withVisualFormat: "H:|-0-[actionLabel]-0-[optionsLabel]-0-|", views: views)
252+
addConstraints(withVisualFormat: "V:|-0-[actionLabel]-(>=0)-|", views: views)
253+
addConstraints(withVisualFormat: "V:|-0-[optionsLabel]-(>=0)-|", views: views)
254+
}
255+
256+
required init?(coder aDecoder: NSCoder) {
257+
fatalError("init(coder:) has not been implemented")
258+
}
259+
}
260+
261+
private extension UIView {
262+
263+
func addAutoLayoutSubviews(_ subviews: [String: UIView]) {
264+
for (_, view) in subviews {
265+
addAutoLayoutSubview(view)
266+
}
267+
}
268+
269+
func addAutoLayoutSubview(_ subview: UIView) {
270+
subview.translatesAutoresizingMaskIntoConstraints = false
271+
addSubview(subview)
272+
}
273+
274+
func addConstraints(withVisualFormat visualFormat: String, views: [String: UIView]) {
275+
addConstraints(NSLayoutConstraint.constraints(withVisualFormat: visualFormat, options: [], metrics: nil, views: views))
276+
}
277+
}

0 commit comments

Comments
 (0)