From 63d511dee88a1a66272f77e68836373540f0743d Mon Sep 17 00:00:00 2001 From: Phillip Thelen Date: Thu, 9 May 2024 14:40:02 +0200 Subject: [PATCH] shop and customization improvements --- HabitRPG/Generated/Strings.swift | 2 + .../Storyboards/Base.lproj/Main.storyboard | 18 +++--- .../Strings/Base.lproj/Mainstrings.strings | 3 +- HabitRPG/Strings/de.lproj/Mainstrings.strings | 1 + .../AvatarDetailViewDataSource.swift | 7 ++- .../AvatarGearDetailViewDataSource.swift | 59 ++++++++++++------- ...SeasonalShopCollectionViewDataSource.swift | 1 + .../UI/General/MainMenuViewController.swift | 2 +- .../AvatarDetailViewController.swift | 2 +- .../AvatarOverviewViewController.swift | 8 ++- HabitRPG/Views/AvatarOverviewItemView.swift | 6 +- 11 files changed, 73 insertions(+), 36 deletions(-) diff --git a/HabitRPG/Generated/Strings.swift b/HabitRPG/Generated/Strings.swift index c3e3ba273..2051a4cf6 100644 --- a/HabitRPG/Generated/Strings.swift +++ b/HabitRPG/Generated/Strings.swift @@ -2045,6 +2045,8 @@ public enum L10n { public static var helpFaq: String { return L10n.tr("Mainstrings", "menu.help_faq") } /// Inventory public static var inventory: String { return L10n.tr("Mainstrings", "menu.inventory") } + /// Quest Shop + public static var questShop: String { return L10n.tr("Mainstrings", "menu.quest_shop") } /// Select Class public static var selectClass: String { return L10n.tr("Mainstrings", "menu.select_class") } /// Shops diff --git a/HabitRPG/Storyboards/Base.lproj/Main.storyboard b/HabitRPG/Storyboards/Base.lproj/Main.storyboard index 70c787398..744c064d6 100644 --- a/HabitRPG/Storyboards/Base.lproj/Main.storyboard +++ b/HabitRPG/Storyboards/Base.lproj/Main.storyboard @@ -830,13 +830,13 @@ - + - + @@ -879,23 +879,23 @@ - + - + - + @@ -903,7 +903,7 @@ - + diff --git a/HabitRPG/Strings/Base.lproj/Mainstrings.strings b/HabitRPG/Strings/Base.lproj/Mainstrings.strings index 0a7bb62f9..09b25c072 100644 --- a/HabitRPG/Strings/Base.lproj/Mainstrings.strings +++ b/HabitRPG/Strings/Base.lproj/Mainstrings.strings @@ -782,11 +782,12 @@ "keep_tasks" = "Keep Tasks"; "delete_tasks" = "Delete Tasks"; "locations.market" = "Market"; -"locations.quest_shop" = "Quests"; +"locations.quest_shop" = "Quest Shop"; "locations.seasonal_shop" = "Seasonal Shop"; "locations.time_travelers_shop" = "Time Travelers"; "locations.customizations" = "Customizations"; "locations.stable" = "Stable"; +"menu.quest_shop" = "Quests"; "NPCs.alex" = "Alex the Merchant"; "NPCs.daniel" = "Daniel the inn keeper"; "NPCs.ian" = "Ian the Quest Guide"; diff --git a/HabitRPG/Strings/de.lproj/Mainstrings.strings b/HabitRPG/Strings/de.lproj/Mainstrings.strings index fe3c8d8ec..51b329d3f 100644 --- a/HabitRPG/Strings/de.lproj/Mainstrings.strings +++ b/HabitRPG/Strings/de.lproj/Mainstrings.strings @@ -721,6 +721,7 @@ "locations.quest_shop" = "Quests"; "locations.seasonal_shop" = "Jahreszeitenmarkt"; "locations.stable" = "Stall"; +"menu.quest_shop" = "Quests"; "NPCs.alex" = "Alex der Händler"; "NPCs.daniel" = "Daniel der Wirt"; "NPCs.ian" = "Ian der Quest-Guide"; diff --git a/HabitRPG/TableViewDataSources/AvatarDetailViewDataSource.swift b/HabitRPG/TableViewDataSources/AvatarDetailViewDataSource.swift index 53be5e747..816397d8d 100644 --- a/HabitRPG/TableViewDataSources/AvatarDetailViewDataSource.swift +++ b/HabitRPG/TableViewDataSources/AvatarDetailViewDataSource.swift @@ -163,6 +163,11 @@ class AvatarDetailViewDataSource: BaseReactiveCollectionViewDataSource Bool in return section.items.isEmpty == false @@ -225,7 +230,7 @@ class AvatarDetailViewDataSource: BaseReactiveCollectionViewDataSource { @@ -15,24 +16,23 @@ class AvatarGearDetailViewDataSource: BaseReactiveCollectionViewDataSource()) var predicate: NSPredicate - if gearType == "eyewear" || gearType == "headAccessory" { - predicate = NSPredicate(format: "gearSet != nil && type == 'headAccessory'") - if gearType == "eyewear" { - predicate = NSPredicate(format: "gearSet == 'glasses' && type == 'eyewear'") - } + if gearType == "headAccessory" { + predicate = NSPredicate(format: "gearSet == 'animal' && type == 'headAccessory'") } else { predicate = NSPredicate(format: "gearSet == 'animal' && type == 'back'") } @@ -89,23 +89,30 @@ class AvatarGearDetailViewDataSource: BaseReactiveCollectionViewDataSource String { + switch gearType { + case "headAccessory": + return L10n.animalEars + case "back": + return L10n.Avatar.animalTails + default: + return "" + } + } + private func configureSections(_ gear: [GearProtocol]) { sections.removeAll() sections.append(ItemSection()) + sections[0].title = getTitle() for gear in gear { - if let set = gear.gearSet { - if let index = sections.firstIndex(where: { (section) -> Bool in - return section.key == set - }) { - sections[index].items.append(gear) - } else { - sections.append(ItemSection(key: set, title: sectionTitle(set))) - sections.last?.items.append(gear) + if newCustomizationLayout { + if !owns(gear: gear) { + continue } - } else { - sections[0].items.append(gear) } + sections[0].items.append(gear) } + sections[0].showIfEmpty = true collectionView?.reloadData() } @@ -126,16 +133,28 @@ class AvatarGearDetailViewDataSource: BaseReactiveCollectionViewDataSource CGSize { + return CGSize(width: collectionView.frame.width, height: 80) + } + override func collectionView(_ collectionView: UICollectionView, viewForSupplementaryElementOfKind kind: String, at indexPath: IndexPath) -> UICollectionReusableView { let view = super.collectionView(collectionView, viewForSupplementaryElementOfKind: kind, at: indexPath) let section = visibleSections[indexPath.section] if let headerView = view as? CustomizationHeaderView { - headerView.label.text = section.title - headerView.label.textColor = ThemeService.shared.theme.primaryTextColor + headerView.label.text = section.title?.localizedUppercase + headerView.label.textColor = ThemeService.shared.theme.quadTextColor } if let footerView = view as? CustomizationFooterView { - footerView.isHidden = true + if newCustomizationLayout && indexPath.section == collectionView.numberOfSections - 1 { + footerView.purchaseButton.isHidden = true + footerView.hostingView.isHidden = false + let hostView = UIHostingView(rootView: CTAFooterView(type: gearType, hasItems: !sections[0].items.isEmpty)) + footerView.hostingView.addSubview(hostView) + hostView.frame = CGRect(x: 0, y: 0, width: collectionView.frame.width, height: 200) + } else { + footerView.isHidden = true + } } return view diff --git a/HabitRPG/TableViewDataSources/SeasonalShopCollectionViewDataSource.swift b/HabitRPG/TableViewDataSources/SeasonalShopCollectionViewDataSource.swift index 080511b57..efba04dd3 100644 --- a/HabitRPG/TableViewDataSources/SeasonalShopCollectionViewDataSource.swift +++ b/HabitRPG/TableViewDataSources/SeasonalShopCollectionViewDataSource.swift @@ -18,6 +18,7 @@ class SeasonalShopCollectionViewDataSource: ShopCollectionViewDataSource { }) { let newSection = ItemSection(title: category.text) newSection.items = category.items + newSection.endDate = category.endDate sections.append(newSection) } collectionView?.reloadData() diff --git a/HabitRPG/UI/General/MainMenuViewController.swift b/HabitRPG/UI/General/MainMenuViewController.swift index eded93054..930f1b8e8 100644 --- a/HabitRPG/UI/General/MainMenuViewController.swift +++ b/HabitRPG/UI/General/MainMenuViewController.swift @@ -89,7 +89,7 @@ class MenuItem { MenuItem(key: .stats, title: L10n.Titles.stats, vcInstantiator: StoryboardScene.User.attributePointsViewController.instantiate), MenuItem(key: .achievements, title: L10n.Titles.achievements, vcInstantiator: StoryboardScene.User.achievementsCollectionViewController.instantiate), MenuItem(key: .market, title: L10n.Locations.market, segue: StoryboardSegue.Main.showMarketSegue.rawValue), - MenuItem(key: .questShop, title: L10n.Locations.questShop, segue: StoryboardSegue.Main.showQuestShopSegue.rawValue), + MenuItem(key: .questShop, title: L10n.Menu.questShop, segue: StoryboardSegue.Main.showQuestShopSegue.rawValue), MenuItem(key: .seasonalShop, title: L10n.Locations.seasonalShop, segue: StoryboardSegue.Main.showSeasonalShopSegue.rawValue), MenuItem(key: .customizationShop, title: L10n.Locations.customizations, segue: StoryboardSegue.Main.showCustomizationShopSegue.rawValue, isHidden: true), MenuItem(key: .timeTravelersShop, title: L10n.Locations.timeTravelersShop, segue: StoryboardSegue.Main.showTimeTravelersSegue.rawValue), diff --git a/HabitRPG/UI/Inventory/AvatarDetailViewController.swift b/HabitRPG/UI/Inventory/AvatarDetailViewController.swift index 951407cbe..15d5ccd03 100644 --- a/HabitRPG/UI/Inventory/AvatarDetailViewController.swift +++ b/HabitRPG/UI/Inventory/AvatarDetailViewController.swift @@ -31,7 +31,7 @@ class AvatarDetailViewController: BaseCollectionViewController, UICollectionView if let type = customizationType { if type == "eyewear" || type == "headAccessory" || type == "back" || type == "animalTails" { - gearDataSource = AvatarGearDetailViewDataSource(type: type) + gearDataSource = AvatarGearDetailViewDataSource(type: type, newCustomizationLayout: newCustomizationLayout) gearDataSource?.collectionView = collectionView } else { customizationDataSource = AvatarDetailViewDataSource(type: type, group: customizationGroup, newCustomizationLayout: newCustomizationLayout) diff --git a/HabitRPG/UI/Inventory/AvatarOverviewViewController.swift b/HabitRPG/UI/Inventory/AvatarOverviewViewController.swift index 82177e7b3..3f5a0ae83 100644 --- a/HabitRPG/UI/Inventory/AvatarOverviewViewController.swift +++ b/HabitRPG/UI/Inventory/AvatarOverviewViewController.swift @@ -55,7 +55,11 @@ class AvatarOverviewViewController: BaseUIViewController, UIScrollViewDelegate { override func applyTheme(theme: Theme) { super.applyTheme(theme: theme) bodySizeLabel.textColor = theme.primaryTextColor - containerview.backgroundColor = theme.offsetBackgroundColor + if theme.isDark { + containerview.backgroundColor = .gray10 + } else { + containerview.backgroundColor = theme.offsetBackgroundColor + } } override func populateText() { @@ -97,7 +101,7 @@ class AvatarOverviewViewController: BaseUIViewController, UIScrollViewDelegate { wheelchairView.setup(title: L10n.Avatar.wheelchair) {[weak self] in self?.openDetailView(type: "chair") } - animalEarsView.setup(title: L10n.Avatar.head) {[weak self] in + animalEarsView.setup(title: L10n.animalEars) {[weak self] in self?.openDetailView(type: "headAccessory") } backgroundView.setup(title: L10n.Avatar.background) {[weak self] in diff --git a/HabitRPG/Views/AvatarOverviewItemView.swift b/HabitRPG/Views/AvatarOverviewItemView.swift index fa74f31f3..373d4c19d 100644 --- a/HabitRPG/Views/AvatarOverviewItemView.swift +++ b/HabitRPG/Views/AvatarOverviewItemView.swift @@ -11,7 +11,11 @@ import UIKit class AvatarOverviewItemView: UIView { var imageView: NetworkImageView = { let imageView = NetworkImageView() - imageView.backgroundColor = ThemeService.shared.theme.windowBackgroundColor + if ThemeService.shared.theme.isDark { + imageView.backgroundColor = .gray50 + } else { + imageView.backgroundColor = ThemeService.shared.theme.windowBackgroundColor + } imageView.layer.cornerRadius = 4 imageView.contentMode = .center return imageView