diff options
author | Nicholas Tay <nick@windblume.net> | 2022-03-24 17:07:51 +1100 |
---|---|---|
committer | Nicholas Tay <nick@windblume.net> | 2022-03-24 17:07:51 +1100 |
commit | d8624dbf8a9111f931802cbb2759ebd009096552 (patch) | |
tree | c0154b234a8274374aada77fd7a63d5dabf00e7e | |
parent | 1b292bc251b3dbef532dacad9705bd197ac4227b (diff) | |
download | forayios-d8624dbf8a9111f931802cbb2759ebd009096552.tar.gz forayios-d8624dbf8a9111f931802cbb2759ebd009096552.tar.bz2 forayios-d8624dbf8a9111f931802cbb2759ebd009096552.zip |
First attempt at Presenter
This is admittedly pretty hard for me to wrap my head around, and I'm
not even using background threading explicitly yet. Will improve.
Diffstat (limited to '')
-rw-r--r-- | foray.xcodeproj/project.pbxproj | 24 | ||||
-rw-r--r-- | foray/Coordinators/ForayCoordinator.swift | 6 | ||||
-rw-r--r-- | foray/ForayItems.swift | 25 | ||||
-rw-r--r-- | foray/ForayModels.swift | 20 | ||||
-rw-r--r-- | foray/ForayViewModels.swift | 16 | ||||
-rw-r--r-- | foray/Presenters/PenguinItemPresenter.swift | 32 | ||||
-rw-r--r-- | foray/Scenes/ForayTableViewController.swift | 40 |
7 files changed, 108 insertions, 55 deletions
diff --git a/foray.xcodeproj/project.pbxproj b/foray.xcodeproj/project.pbxproj index e25da72..176b21c 100644 --- a/foray.xcodeproj/project.pbxproj +++ b/foray.xcodeproj/project.pbxproj @@ -8,7 +8,7 @@ /* Begin PBXBuildFile section */ C011E4F127E6211400C248D6 /* ForayNetworkManager.swift in Sources */ = {isa = PBXBuildFile; fileRef = C011E4F027E6211400C248D6 /* ForayNetworkManager.swift */; }; - C011E4F327E6216C00C248D6 /* ForayItems.swift in Sources */ = {isa = PBXBuildFile; fileRef = C011E4F227E6216C00C248D6 /* ForayItems.swift */; }; + C011E4F327E6216C00C248D6 /* ForayModels.swift in Sources */ = {isa = PBXBuildFile; fileRef = C011E4F227E6216C00C248D6 /* ForayModels.swift */; }; C049BBFE27E82B9E003820A9 /* Coordinator.swift in Sources */ = {isa = PBXBuildFile; fileRef = C049BBFD27E82B9E003820A9 /* Coordinator.swift */; }; C049BC0027E82C90003820A9 /* ForayCoordinator.swift in Sources */ = {isa = PBXBuildFile; fileRef = C049BBFF27E82C90003820A9 /* ForayCoordinator.swift */; }; C04B45A427DEF117001451A3 /* AppDelegate.swift in Sources */ = {isa = PBXBuildFile; fileRef = C04B45A327DEF117001451A3 /* AppDelegate.swift */; }; @@ -20,12 +20,14 @@ C09676BA27E86B6E00353D46 /* ForayLoadingOverlay.swift in Sources */ = {isa = PBXBuildFile; fileRef = C09676B927E86B6E00353D46 /* ForayLoadingOverlay.swift */; }; C09676BC27EC27E700353D46 /* UIViewController+Extensions.swift in Sources */ = {isa = PBXBuildFile; fileRef = C09676BB27EC27E700353D46 /* UIViewController+Extensions.swift */; }; C09676BE27EC28B100353D46 /* ForayDetailView.swift in Sources */ = {isa = PBXBuildFile; fileRef = C09676BD27EC28B100353D46 /* ForayDetailView.swift */; }; + C0C73E6427EC3A650015497D /* ForayViewModels.swift in Sources */ = {isa = PBXBuildFile; fileRef = C0C73E6327EC3A650015497D /* ForayViewModels.swift */; }; + C0C73E6727EC3BA50015497D /* PenguinItemPresenter.swift in Sources */ = {isa = PBXBuildFile; fileRef = C0C73E6627EC3BA50015497D /* PenguinItemPresenter.swift */; }; C0FEAF5F27E14C52000A7648 /* ForayDetailViewController.swift in Sources */ = {isa = PBXBuildFile; fileRef = C0FEAF5E27E14C52000A7648 /* ForayDetailViewController.swift */; }; /* End PBXBuildFile section */ /* Begin PBXFileReference section */ C011E4F027E6211400C248D6 /* ForayNetworkManager.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ForayNetworkManager.swift; sourceTree = "<group>"; }; - C011E4F227E6216C00C248D6 /* ForayItems.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ForayItems.swift; sourceTree = "<group>"; }; + C011E4F227E6216C00C248D6 /* ForayModels.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ForayModels.swift; sourceTree = "<group>"; }; C049BBFD27E82B9E003820A9 /* Coordinator.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = Coordinator.swift; sourceTree = "<group>"; }; C049BBFF27E82C90003820A9 /* ForayCoordinator.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ForayCoordinator.swift; sourceTree = "<group>"; }; C04B45A027DEF117001451A3 /* foray.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = foray.app; sourceTree = BUILT_PRODUCTS_DIR; }; @@ -38,6 +40,8 @@ C09676B927E86B6E00353D46 /* ForayLoadingOverlay.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ForayLoadingOverlay.swift; sourceTree = "<group>"; }; C09676BB27EC27E700353D46 /* UIViewController+Extensions.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "UIViewController+Extensions.swift"; sourceTree = "<group>"; }; C09676BD27EC28B100353D46 /* ForayDetailView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ForayDetailView.swift; sourceTree = "<group>"; }; + C0C73E6327EC3A650015497D /* ForayViewModels.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ForayViewModels.swift; sourceTree = "<group>"; }; + C0C73E6627EC3BA50015497D /* PenguinItemPresenter.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = PenguinItemPresenter.swift; sourceTree = "<group>"; }; C0FEAF5E27E14C52000A7648 /* ForayDetailViewController.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ForayDetailViewController.swift; sourceTree = "<group>"; }; /* End PBXFileReference section */ @@ -72,12 +76,14 @@ C04B45A227DEF117001451A3 /* foray */ = { isa = PBXGroup; children = ( + C0C73E6527EC3B8F0015497D /* Presenters */, C09676C327EC358F00353D46 /* Coordinators */, C09676C227EC354700353D46 /* Extensions */, C09676C127EC353D00353D46 /* Scenes */, C04B45A327DEF117001451A3 /* AppDelegate.swift */, C04B45A527DEF117001451A3 /* SceneDelegate.swift */, - C011E4F227E6216C00C248D6 /* ForayItems.swift */, + C011E4F227E6216C00C248D6 /* ForayModels.swift */, + C0C73E6327EC3A650015497D /* ForayViewModels.swift */, C011E4F027E6211400C248D6 /* ForayNetworkManager.swift */, C04B45AC27DEF118001451A3 /* Assets.xcassets */, C04B45B127DEF118001451A3 /* Info.plist */, @@ -114,6 +120,14 @@ path = Coordinators; sourceTree = "<group>"; }; + C0C73E6527EC3B8F0015497D /* Presenters */ = { + isa = PBXGroup; + children = ( + C0C73E6627EC3BA50015497D /* PenguinItemPresenter.swift */, + ); + path = Presenters; + sourceTree = "<group>"; + }; /* End PBXGroup section */ /* Begin PBXNativeTarget section */ @@ -195,11 +209,13 @@ C09676BE27EC28B100353D46 /* ForayDetailView.swift in Sources */, C04B45B827DEF2ED001451A3 /* ForayTableViewController.swift in Sources */, C0FEAF5F27E14C52000A7648 /* ForayDetailViewController.swift in Sources */, + C0C73E6427EC3A650015497D /* ForayViewModels.swift in Sources */, C04EDE4427E4298D00D83005 /* ForayNewTableViewCell.swift in Sources */, C09676BC27EC27E700353D46 /* UIViewController+Extensions.swift in Sources */, C04B45A427DEF117001451A3 /* AppDelegate.swift in Sources */, C09676BA27E86B6E00353D46 /* ForayLoadingOverlay.swift in Sources */, - C011E4F327E6216C00C248D6 /* ForayItems.swift in Sources */, + C011E4F327E6216C00C248D6 /* ForayModels.swift in Sources */, + C0C73E6727EC3BA50015497D /* PenguinItemPresenter.swift in Sources */, C04B45A627DEF117001451A3 /* SceneDelegate.swift in Sources */, ); runOnlyForDeploymentPostprocessing = 0; diff --git a/foray/Coordinators/ForayCoordinator.swift b/foray/Coordinators/ForayCoordinator.swift index 6497ec0..6c4bb3f 100644 --- a/foray/Coordinators/ForayCoordinator.swift +++ b/foray/Coordinators/ForayCoordinator.swift @@ -33,7 +33,7 @@ class ForayCoordinator: Coordinator { let detailViewController = ForayDetailViewController() - func showDetails(item: PenguinItem) { + func showDetails(item: PenguinItemViewModel) { let image: UIImage var description: String = "Type: " switch item.type { @@ -45,9 +45,7 @@ class ForayCoordinator: Coordinator { image = UIImage(named: "spy")! } description += "\nID: " + item.id - let dateFormatter = DateFormatter() - dateFormatter.dateFormat = "yyyy-MM-dd" - description += "\nReleased: " + dateFormatter.string(from: item.releaseDate) + description += "\nReleased: " + item.releaseDateFormatted detailViewController.setDetails(name: item.name, description: description, image: image) push(vc: detailViewController) diff --git a/foray/ForayItems.swift b/foray/ForayItems.swift deleted file mode 100644 index a8786ee..0000000 --- a/foray/ForayItems.swift +++ /dev/null @@ -1,25 +0,0 @@ -// -// ForayItems.swift -// foray -// -// Created by Nicholas Tay on 20/3/2022. -// - -import Foundation - -enum ItemType: String, Decodable { - case item - case quest -} - -struct YearSection { - var year: Int - var items: [PenguinItem] -} - -struct PenguinItem: Decodable { - var type: ItemType - var releaseDate: Date - var id: String - var name: String -} diff --git a/foray/ForayModels.swift b/foray/ForayModels.swift new file mode 100644 index 0000000..c721b95 --- /dev/null +++ b/foray/ForayModels.swift @@ -0,0 +1,20 @@ +// +// ForayItems.swift +// foray +// +// Created by Nicholas Tay on 20/3/2022. +// + +import Foundation + +enum PenguinItemType: String, Decodable { + case item + case quest +} + +struct PenguinItemModel: Decodable { + let type: PenguinItemType + let releaseDate: Date + let id: String + let name: String +} diff --git a/foray/ForayViewModels.swift b/foray/ForayViewModels.swift new file mode 100644 index 0000000..9b9b058 --- /dev/null +++ b/foray/ForayViewModels.swift @@ -0,0 +1,16 @@ +// +// ForayViewModels.swift +// foray +// +// Created by Nicholas Tay on 24/3/2022. +// + +import Foundation + +struct PenguinItemViewModel { + let type: PenguinItemType + let releaseDateFormatted: String + let year: Int + let id: String + let name: String +} diff --git a/foray/Presenters/PenguinItemPresenter.swift b/foray/Presenters/PenguinItemPresenter.swift new file mode 100644 index 0000000..0420825 --- /dev/null +++ b/foray/Presenters/PenguinItemPresenter.swift @@ -0,0 +1,32 @@ +// +// PenguinItemPresenter.swift +// foray +// +// Created by Nicholas Tay on 24/3/2022. +// + +import Foundation + +class PenguinItemPresenter { + func getData(onComplete: @escaping ([PenguinItemViewModel]) -> ()) { + ForayNetworkManager.shared.get( + url: "https://users.windblume.net/~nick/upload/dummy.json", + onComplete: { (apiItems: [PenguinItemModel]) in + onComplete(self.transform(models: apiItems)) + }) + } + + func transform(models: [PenguinItemModel]) -> [PenguinItemViewModel] { + let dateFormatter = DateFormatter() + dateFormatter.dateFormat = "yyyy-MM-dd" + + return models + .sorted { $0.releaseDate < $1.releaseDate } + .map { + PenguinItemViewModel(type: $0.type, + releaseDateFormatted: dateFormatter.string(from: $0.releaseDate), + year: Calendar.current.component(.year, from: $0.releaseDate), + id: $0.id, name: $0.name) + } + } +} diff --git a/foray/Scenes/ForayTableViewController.swift b/foray/Scenes/ForayTableViewController.swift index 37ac2e5..ed44139 100644 --- a/foray/Scenes/ForayTableViewController.swift +++ b/foray/Scenes/ForayTableViewController.swift @@ -7,8 +7,14 @@ import UIKit +struct YearSection { + var year: Int + var items: [PenguinItemViewModel] +} + class ForayTableViewController: UITableViewController, ForayCoordinated { + let presenter: PenguinItemPresenter = PenguinItemPresenter() var coordinator: ForayCoordinator? // MARK: - Static data TEMP @@ -39,28 +45,18 @@ class ForayTableViewController: UITableViewController, ForayCoordinated { } func reloadApiData() { - ForayNetworkManager.shared.get( - url: "https://users.windblume.net/~nick/upload/dummy.json", - onComplete: { (apiItems: [PenguinItem]) in - var items = apiItems - - // Show items in chronological order within sections - items.sort { (lhs, rhs) in lhs.releaseDate < rhs.releaseDate } - - // Group by year sections - let groups = Dictionary(grouping: apiItems) { (item) in - return Calendar.current.component(.year, from: item.releaseDate) - } - self.sections = groups.map { (key, values) in - return YearSection(year: key, items: values) - } - // Sort the sections from oldest year to newest - self.sections.sort { (lhs, rhs) in lhs.year < rhs.year } - - self.tableView.reloadData() - self.refreshControl?.endRefreshing() - self.coordinator?.hideLoading() - }) + presenter.getData(onComplete: { (data: [PenguinItemViewModel]) in + let groups = Dictionary(grouping: data) { $0.year } + self.sections = groups.map { (key, values) in + return YearSection(year: key, items: values) + } + // Sort the sections from oldest year to newest + self.sections.sort { (lhs, rhs) in lhs.year < rhs.year } + + self.tableView.reloadData() + self.refreshControl?.endRefreshing() + self.coordinator?.hideLoading() + }) } // MARK: - Table view data source |