Skip to content

Commit 6994e7d

Browse files
committed
Stats Insights: Added empty state to latest post summary cell
1 parent 4f28219 commit 6994e7d

1 file changed

Lines changed: 87 additions & 39 deletions

File tree

WordPress/Classes/ViewRelated/Stats/Insights/StatsLatestPostSummaryInsightsCell.swift

Lines changed: 87 additions & 39 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,5 @@
11
import UIKit
2+
import Gridicons
23

34

45
class StatsLatestPostSummaryInsightsCell: StatsBaseCell, LatestPostSummaryConfigurable {
@@ -8,14 +9,19 @@ class StatsLatestPostSummaryInsightsCell: StatsBaseCell, LatestPostSummaryConfig
89
private var lastPostDetails: StatsPostDetails?
910
private var postTitle = StatSection.noPostTitle
1011

11-
private var statsStackView: UIStackView!
12+
private let outerStackView = UIStackView()
13+
private let postStackView = UIStackView()
14+
private let statsStackView = UIStackView()
1215
private let postTitleLabel = UILabel()
1316
private let postTimestampLabel = UILabel()
1417
private let viewCountLabel = UILabel()
1518
private let likeCountLabel = UILabel()
1619
private let commentCountLabel = UILabel()
1720
private let postImageView = CachedAnimatedImageView()
1821

22+
private let noDataLabel = UILabel()
23+
private let createPostButton = UIButton(type: .system)
24+
1925
lazy var imageLoader: ImageLoader = {
2026
return ImageLoader(imageView: postImageView, gifStrategy: .mediumGIFs)
2127
}()
@@ -32,42 +38,46 @@ class StatsLatestPostSummaryInsightsCell: StatsBaseCell, LatestPostSummaryConfig
3238
fatalError()
3339
}
3440

41+
override func prepareForReuse() {
42+
super.prepareForReuse()
43+
44+
toggleNoData(show: false)
45+
}
46+
3547
// MARK: - View Configuration
3648

3749
private func configureView() {
38-
let stackView = makeOuterStackView()
39-
contentView.addSubview(stackView)
50+
configureOuterStackView()
51+
contentView.addSubview(outerStackView)
4052

41-
let postStackView = makePostStackView()
42-
statsStackView = makeStatsStackView()
43-
stackView.addArrangedSubview(postStackView)
44-
stackView.addArrangedSubview(statsStackView)
53+
configurePostStackView()
54+
configureStatsStackView()
55+
outerStackView.addArrangedSubview(postStackView)
56+
outerStackView.addArrangedSubview(statsStackView)
4557

46-
topConstraint = stackView.topAnchor.constraint(equalTo: contentView.topAnchor, constant: StatsBaseCell.Metrics.padding)
58+
topConstraint = outerStackView.topAnchor.constraint(equalTo: contentView.topAnchor, constant: StatsBaseCell.Metrics.padding)
4759

4860
NSLayoutConstraint.activate([
4961
topConstraint,
50-
stackView.bottomAnchor.constraint(equalTo: contentView.bottomAnchor, constant: -StatsBaseCell.Metrics.padding),
51-
stackView.leadingAnchor.constraint(equalTo: contentView.leadingAnchor, constant: StatsBaseCell.Metrics.padding),
52-
stackView.trailingAnchor.constraint(equalTo: contentView.trailingAnchor, constant: -StatsBaseCell.Metrics.padding),
62+
outerStackView.bottomAnchor.constraint(equalTo: contentView.bottomAnchor, constant: -StatsBaseCell.Metrics.padding),
63+
outerStackView.leadingAnchor.constraint(equalTo: contentView.leadingAnchor, constant: StatsBaseCell.Metrics.padding),
64+
outerStackView.trailingAnchor.constraint(equalTo: contentView.trailingAnchor, constant: -StatsBaseCell.Metrics.padding),
5365
])
54-
}
5566

56-
private func makeOuterStackView() -> UIStackView {
57-
let stackView = UIStackView()
58-
stackView.translatesAutoresizingMaskIntoConstraints = false
59-
stackView.axis = .vertical
60-
stackView.spacing = Metrics.outerStackViewSpacing
67+
configureNoDataViews()
68+
}
6169

62-
return stackView
70+
private func configureOuterStackView() {
71+
outerStackView.translatesAutoresizingMaskIntoConstraints = false
72+
outerStackView.axis = .vertical
73+
outerStackView.spacing = Metrics.outerStackViewSpacing
6374
}
6475

65-
private func makePostStackView() -> UIStackView {
66-
let stackView = UIStackView()
67-
stackView.translatesAutoresizingMaskIntoConstraints = false
68-
stackView.axis = .horizontal
69-
stackView.alignment = .top
70-
stackView.spacing = Metrics.postStackViewHorizontalSpacing
76+
private func configurePostStackView() {
77+
postStackView.translatesAutoresizingMaskIntoConstraints = false
78+
postStackView.axis = .horizontal
79+
postStackView.alignment = .top
80+
postStackView.spacing = Metrics.postStackViewHorizontalSpacing
7181

7282
let postInfoStackView = UIStackView()
7383
postInfoStackView.translatesAutoresizingMaskIntoConstraints = false
@@ -94,17 +104,14 @@ class StatsLatestPostSummaryInsightsCell: StatsBaseCell, LatestPostSummaryConfig
94104
postImageView.layer.cornerRadius = Metrics.thumbnailCornerRadius
95105
postImageView.layer.masksToBounds = true
96106

97-
stackView.addArrangedSubviews([postInfoStackView, postImageView])
98-
99-
return stackView
107+
postStackView.addArrangedSubviews([postInfoStackView, postImageView])
100108
}
101109

102-
private func makeStatsStackView() -> UIStackView {
103-
let stackView = UIStackView()
104-
stackView.translatesAutoresizingMaskIntoConstraints = false
105-
stackView.axis = .horizontal
106-
stackView.alignment = .top
107-
stackView.spacing = Metrics.postStackViewHorizontalSpacing
110+
private func configureStatsStackView() {
111+
statsStackView.translatesAutoresizingMaskIntoConstraints = false
112+
statsStackView.axis = .horizontal
113+
statsStackView.alignment = .top
114+
statsStackView.spacing = Metrics.postStackViewHorizontalSpacing
108115

109116
let viewsStack = makeVerticalStatsStackView(with: viewCountLabel, title: TextContent.views)
110117
let likesStack = makeVerticalStatsStackView(with: likeCountLabel, title: TextContent.likes)
@@ -113,7 +120,7 @@ class StatsLatestPostSummaryInsightsCell: StatsBaseCell, LatestPostSummaryConfig
113120
let divider1 = makeVerticalDivider()
114121
let divider2 = makeVerticalDivider()
115122

116-
stackView.addArrangedSubviews([
123+
statsStackView.addArrangedSubviews([
117124
viewsStack,
118125
divider1,
119126
likesStack,
@@ -124,11 +131,9 @@ class StatsLatestPostSummaryInsightsCell: StatsBaseCell, LatestPostSummaryConfig
124131
NSLayoutConstraint.activate([
125132
viewsStack.widthAnchor.constraint(equalTo: likesStack.widthAnchor),
126133
likesStack.widthAnchor.constraint(equalTo: commentsStack.widthAnchor),
127-
divider1.heightAnchor.constraint(equalTo: stackView.heightAnchor),
128-
divider2.heightAnchor.constraint(equalTo: stackView.heightAnchor)
134+
divider1.heightAnchor.constraint(equalTo: statsStackView.heightAnchor),
135+
divider2.heightAnchor.constraint(equalTo: statsStackView.heightAnchor)
129136
])
130-
131-
return stackView
132137
}
133138

134139
private func makeVerticalStatsStackView(with countLabel: UILabel, title: String) -> UIStackView {
@@ -162,14 +167,30 @@ class StatsLatestPostSummaryInsightsCell: StatsBaseCell, LatestPostSummaryConfig
162167
return divider
163168
}
164169

170+
private func configureNoDataViews() {
171+
noDataLabel.font = .preferredFont(forTextStyle: .body)
172+
noDataLabel.textColor = .textSubtle
173+
noDataLabel.numberOfLines = 0
174+
noDataLabel.text = TextContent.noData
175+
176+
createPostButton.setImage(.gridicon(.create), for: .normal)
177+
createPostButton.setTitle(TextContent.createPost, for: .normal)
178+
179+
// Increase the padding between the image and title of the button
180+
createPostButton.titleEdgeInsets = UIEdgeInsets(top: 0, left: Metrics.createPostButtonInset, bottom: 0, right: -Metrics.createPostButtonInset)
181+
createPostButton.contentEdgeInsets = UIEdgeInsets(top: 0, left: 0, bottom: 0, right: Metrics.createPostButtonInset)
182+
183+
createPostButton.addTarget(self, action: #selector(createPostTapped), for: .touchUpInside)
184+
}
185+
165186
// MARK: - Public Configuration
166187

167188
func configure(withInsightData lastPostInsight: StatsLastPostInsight?, chartData: StatsPostDetails?, andDelegate delegate: SiteStatsInsightsDelegate?) {
168189
siteStatsInsightsDelegate = delegate
169190
statSection = .insightsLatestPostSummary
170191

171192
guard let lastPostInsight = lastPostInsight else {
172-
// Old cell shows Create Post if there's no latest post
193+
toggleNoData(show: true)
173194
return
174195
}
175196

@@ -186,6 +207,22 @@ class StatsLatestPostSummaryInsightsCell: StatsBaseCell, LatestPostSummaryConfig
186207
commentCountLabel.text = lastPostInsight.commentsCount.abbreviatedString()
187208
}
188209

210+
// Switches out the no data views into the main stack view if we have no data.
211+
//
212+
private func toggleNoData(show: Bool) {
213+
if !show && outerStackView.subviews.contains(noDataLabel) {
214+
noDataLabel.removeFromSuperview()
215+
createPostButton.removeFromSuperview()
216+
outerStackView.addArrangedSubviews([postStackView, statsStackView])
217+
outerStackView.alignment = .fill
218+
} else if show && outerStackView.subviews.contains(postStackView) {
219+
postStackView.removeFromSuperview()
220+
statsStackView.removeFromSuperview()
221+
outerStackView.addArrangedSubviews([noDataLabel, createPostButton])
222+
outerStackView.alignment = .leading
223+
}
224+
}
225+
189226
private func configureFeaturedImage(url: URL?) {
190227
if let url = url,
191228
let siteID = SiteStatsInformation.sharedInstance.siteID?.intValue,
@@ -202,17 +239,28 @@ class StatsLatestPostSummaryInsightsCell: StatsBaseCell, LatestPostSummaryConfig
202239
}
203240
}
204241

242+
// MARK: - Actions
243+
244+
@objc func createPostTapped() {
245+
siteStatsInsightsDelegate?.showCreatePost?()
246+
}
247+
248+
// MARK: - Constants
249+
205250
private enum Metrics {
206251
static let outerStackViewSpacing: CGFloat = 16.0
207252
static let postStackViewHorizontalSpacing: CGFloat = 16.0
208253
static let postStackViewVerticalSpacing: CGFloat = 8.0
209254
static let statsStackViewVerticalSpacing: CGFloat = 8.0
255+
static let createPostButtonInset: CGFloat = 8.0
210256
static let thumbnailSize: CGFloat = 68.0
211257
static let thumbnailCornerRadius: CGFloat = 4.0
212258
static let dividerWidth: CGFloat = 1.0
213259
}
214260

215261
private enum TextContent {
262+
static let noData = NSLocalizedString("stats.insights.latestPostSummary.noData", value: "You haven't published any posts yet. Check back later once you've published your first post!", comment: "Prompt shown in the 'Latest Post Summary' stats card if a user hasn't yet published anything.")
263+
static let createPost = NSLocalizedString("stats.insights.latestPostSummary.createPost", value: "Create Post", comment: "Title of button shown in Stats prompting the user to create a post on their site.")
216264
static let publishDate = NSLocalizedString("stats.insights.latestPostSummary.publishDate", value: "Published %@", comment: "Publish date of a post displayed in Stats. Placeholder will be replaced with a localized relative time, e.g. 2 days ago")
217265
static let views = NSLocalizedString("stats.insights.latestPostSummary.views", value: "Views", comment: "Title for Views count in Latest Post Summary stats card.")
218266
static let likes = NSLocalizedString("stats.insights.latestPostSummary.likes", value: "Likes", comment: "Title for Likes count in Latest Post Summary stats card.")

0 commit comments

Comments
 (0)