Skip to content

Commit da971f5

Browse files
committed
feat: introduced HubMenuBadge view in HubMenuElement
1 parent 2b8b394 commit da971f5

File tree

2 files changed

+45
-16
lines changed

2 files changed

+45
-16
lines changed

WooCommerce/Classes/ViewRelated/Hub Menu/HubMenu.swift

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -30,7 +30,8 @@ struct HubMenu: View {
3030

3131
LazyVGrid(columns: gridItemLayout, spacing: Constants.itemSpacing) {
3232
ForEach(viewModel.menuElements, id: \.self) { menu in
33-
HubMenuElement(image: menu.icon, imageColor: menu.iconColor, text: menu.title, onTapGesture: {
33+
let badgeCount = menu == .reviews ? viewModel.reviewsNotificationBadgeCount : 0
34+
HubMenuElement(image: menu.icon, imageColor: menu.iconColor, text: menu.title, badge: badgeCount, onTapGesture: {
3435
switch menu {
3536
case .woocommerceAdmin:
3637
ServiceLocator.analytics.track(.hubMenuOptionTapped, withProperties: [Constants.option: "admin_menu"])

WooCommerce/Classes/ViewRelated/Hub Menu/HubMenuElement.swift

Lines changed: 43 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@ struct HubMenuElement: View {
66
let image: UIImage
77
let imageColor: UIColor
88
let text: String
9+
let badge: Int
910
let onTapGesture: (() -> Void)
1011

1112
@ScaledMetric var imageSize: CGFloat = 58
@@ -15,30 +16,56 @@ struct HubMenuElement: View {
1516
Button {
1617
onTapGesture()
1718
} label: {
18-
VStack {
19-
ZStack {
20-
Color(UIColor(light: .listBackground,
21-
dark: .secondaryButtonBackground))
22-
Image(uiImage: image)
23-
.renderingMode(.template)
24-
.resizable()
25-
.scaledToFit()
26-
.foregroundColor(Color(imageColor))
27-
.frame(width: iconSize, height: iconSize)
19+
ZStack(alignment: .topTrailing) {
20+
21+
VStack {
22+
ZStack {
23+
Color(UIColor(light: .listBackground,
24+
dark: .secondaryButtonBackground))
25+
Image(uiImage: image)
26+
.renderingMode(.template)
27+
.resizable()
28+
.scaledToFit()
29+
.foregroundColor(Color(imageColor))
30+
.frame(width: iconSize, height: iconSize)
31+
}
32+
.frame(width: imageSize, height: imageSize, alignment: .center)
33+
.cornerRadius(imageSize/2)
34+
.padding(.bottom, Constants.paddingBetweenElements)
35+
Text(text)
36+
.bodyStyle()
2837
}
29-
.frame(width: imageSize, height: imageSize, alignment: .center)
30-
.cornerRadius(imageSize/2)
31-
.padding(.bottom, Constants.paddingBetweenElements)
32-
Text(text)
38+
.frame(width: Constants.itemSize, height: Constants.itemSize)
39+
HubMenuBadge(value: badge)
40+
.padding([.top, .trailing], 8)
41+
.renderedIf(badge > 0)
42+
}
43+
}
44+
}
45+
46+
private struct HubMenuBadge: View {
47+
let value: Int
48+
49+
var body: some View {
50+
ZStack (alignment: .center) {
51+
Rectangle()
52+
.fill(.purple)
53+
.cornerRadius(Constants.cornerRadius)
54+
Text(String(value))
55+
.foregroundColor(.white)
3356
.bodyStyle()
57+
.padding([.leading, .trailing], Constants.paddingBetweenElements)
3458
}
35-
.frame(width: Constants.itemSize, height: Constants.itemSize)
59+
.frame(height: Constants.badgeSize)
60+
.fixedSize()
3661
}
3762
}
3863

3964
enum Constants {
4065
static let paddingBetweenElements: CGFloat = 8
4166
static let itemSize: CGFloat = 160
67+
static let badgeSize: CGFloat = 24
68+
static let cornerRadius: CGFloat = badgeSize/2
4269
}
4370
}
4471

@@ -47,6 +74,7 @@ struct HubMenuElement_Previews: PreviewProvider {
4774
HubMenuElement(image: .starOutlineImage(),
4875
imageColor: .blue,
4976
text: "Menu",
77+
badge: 1,
5078
onTapGesture: {})
5179
.previewLayout(.fixed(width: 160, height: 160))
5280
.previewDisplayName("Hub Menu Element")

0 commit comments

Comments
 (0)