Skip to content

Commit 4c6fe1f

Browse files
committed
Merge branch 'master' into fix/issue-178-networking-layer
2 parents 2e2f68d + 5be1f9b commit 4c6fe1f

File tree

15 files changed

+324
-499
lines changed

15 files changed

+324
-499
lines changed

Podfile.lock

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -171,4 +171,4 @@ SPEC CHECKSUMS:
171171

172172
PODFILE CHECKSUM: ad8b2fa0cef07782327d22c0570f1659eddad970
173173

174-
COCOAPODS: 1.10.2
174+
COCOAPODS: 1.11.2

ios-base.xcodeproj/project.pbxproj

Lines changed: 18 additions & 43 deletions
Large diffs are not rendered by default.

ios-base/Base.lproj/Main.storyboard

Lines changed: 0 additions & 300 deletions
This file was deleted.

ios-base/Extensions/LabelExtension.swift

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -13,7 +13,7 @@ extension UILabel {
1313

1414
static func titleLabel (
1515
text: String = "",
16-
font: UIFont = .h1Regular,
16+
font: UIFont = .h2Regular,
1717
textColor: UIColor = .mainTitle,
1818
backgroundColor: UIColor = .clear,
1919
numberOfLines: Int = 0,

ios-base/Extensions/TextFieldExtension.swift

Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,27 @@
99
import UIKit
1010

1111
extension UITextField {
12+
13+
convenience init(
14+
target: Any,
15+
selector: Selector,
16+
placeholder: String,
17+
backgroundColor: UIColor = .white,
18+
height: CGFloat = UI.TextField.height,
19+
borderStyle: BorderStyle = .line,
20+
isPassword: Bool = false
21+
) {
22+
self.init()
23+
24+
translatesAutoresizingMaskIntoConstraints = false
25+
addTarget(target, action: selector, for: .editingChanged)
26+
self.placeholder = placeholder
27+
self.backgroundColor = backgroundColor
28+
self.borderStyle = borderStyle
29+
heightAnchor.constraint(equalToConstant: height).isActive = true
30+
isSecureTextEntry = isPassword
31+
}
32+
1233
func setPlaceholder(color: UIColor = .lightGray) {
1334
attributedPlaceholder = NSAttributedString(
1435
string: placeholder ?? "",

ios-base/Helpers/UIConstants.swift

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -12,10 +12,13 @@ import UIKit
1212
struct UI {
1313
enum Defaults {
1414
static let margin: CGFloat = 32
15+
static let spacing: CGFloat = 20
1516
}
1617

1718
enum ViewController {
1819
static let topMargin: CGFloat = 72
20+
static let smallTopMargin: CGFloat = 40
21+
static let bottomMargin: CGFloat = 60
1922
}
2023

2124
enum Button {
@@ -24,4 +27,8 @@ struct UI {
2427
static let width: CGFloat = 200.0
2528
static let spacing: CGFloat = 20.0
2629
}
30+
31+
enum TextField {
32+
static let height: CGFloat = 40.0
33+
}
2734
}

ios-base/Home/Routes/HomeRoutes.swift

Lines changed: 1 addition & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -15,10 +15,7 @@ enum HomeRoutes: Route {
1515
var screen: UIViewController {
1616
switch self {
1717
case .home:
18-
guard let home = R.storyboard.main.homeViewController() else {
19-
return UIViewController()
20-
}
21-
home.viewModel = HomeViewModel()
18+
let home = HomeViewController(viewModel: HomeViewModel())
2219
return home
2320
}
2421
}

ios-base/Home/Views/HomeViewController.swift

Lines changed: 84 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -12,37 +12,112 @@ class HomeViewController: UIViewController, ActivityIndicatorPresenter {
1212

1313
// MARK: - Outlets
1414

15-
@IBOutlet weak var welcomeLabel: UILabel!
16-
@IBOutlet weak var logOut: UIButton!
17-
@IBOutlet weak var deleteAccountButton: UIButton!
15+
private lazy var welcomeLabel = UILabel.titleLabel(
16+
text: "homescreen_title".localized
17+
)
18+
19+
private lazy var logOutButton = UIButton.primaryButton(
20+
color: .black,
21+
title: "homescreen_logout_button_title".localized,
22+
target: self,
23+
action: #selector(tapOnLogOutButton)
24+
)
25+
26+
private lazy var deleteAccountButton = UIButton.primaryButton(
27+
color: .deleteButton,
28+
title: "homescreen_delete_button_title".localized,
29+
target: self,
30+
action: #selector(tapOnDeleteAccount)
31+
)
32+
33+
private lazy var getProfileButton: UIButton = {
34+
let button = UIButton()
35+
button.translatesAutoresizingMaskIntoConstraints = false
36+
button.setTitle("homescreen_get_profile_button_title".localized, for: .normal)
37+
button.setTitleColor(.blue, for: .normal)
38+
button.addTarget(
39+
self,
40+
action: #selector(tapOnGetMyProfile),
41+
for: .touchUpInside
42+
)
43+
44+
return button
45+
}()
1846

1947
let activityIndicator = UIActivityIndicatorView()
2048

21-
var viewModel: HomeViewModel!
49+
private var viewModel: HomeViewModel
50+
51+
init(viewModel: HomeViewModel) {
52+
self.viewModel = viewModel
53+
super.init(nibName: nil, bundle: nil)
54+
}
55+
56+
@available(*, unavailable)
57+
required init?(coder: NSCoder) {
58+
fatalError("init(coder:) has not been implemented")
59+
}
2260

2361
// MARK: - Lifecycle Events
2462
override func viewDidLoad() {
2563
super.viewDidLoad()
64+
2665
viewModel.delegate = self
27-
logOut.setRoundBorders(22)
28-
deleteAccountButton.setRoundBorders(22)
66+
configureViews()
2967
}
3068

3169
// MARK: - Actions
3270

33-
@IBAction func tapOnGetMyProfile(_ sender: Any) {
71+
@objc
72+
func tapOnGetMyProfile(_ sender: Any) {
3473
viewModel.loadUserProfile()
3574
}
3675

37-
@IBAction func tapOnLogOutButton(_ sender: Any) {
76+
@objc
77+
func tapOnLogOutButton(_ sender: Any) {
3878
viewModel.logoutUser()
3979
}
4080

41-
@IBAction func tapOnDeleteAccount(_ sender: Any) {
81+
@objc
82+
func tapOnDeleteAccount(_ sender: Any) {
4283
viewModel.deleteAccount()
4384
}
4485
}
4586

87+
private extension HomeViewController {
88+
89+
private func configureViews() {
90+
applyDefaultUIConfigs()
91+
view.addSubviews(
92+
subviews: [welcomeLabel, logOutButton, deleteAccountButton, getProfileButton]
93+
)
94+
activateConstraints()
95+
}
96+
97+
private func activateConstraints() {
98+
welcomeLabel.centerHorizontally(with: view)
99+
getProfileButton.center(view)
100+
logOutButton.attachHorizontally(to: view)
101+
deleteAccountButton.attachHorizontally(to: view)
102+
103+
NSLayoutConstraint.activate([
104+
welcomeLabel.topAnchor.constraint(
105+
equalTo: view.topAnchor,
106+
constant: UI.ViewController.topMargin
107+
),
108+
deleteAccountButton.bottomAnchor.constraint(
109+
equalTo: view.bottomAnchor,
110+
constant: -UI.Defaults.margin
111+
),
112+
logOutButton.bottomAnchor.constraint(
113+
equalTo: deleteAccountButton.topAnchor,
114+
constant: -UI.Button.spacing
115+
)
116+
])
117+
}
118+
119+
}
120+
46121
extension HomeViewController: HomeViewModelDelegate {
47122
func didUpdateState(to state: HomeViewModelState) {
48123
switch state {

ios-base/Networking/Services/BaseAPIClient.swift

Lines changed: 11 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -71,8 +71,10 @@ internal final class BaseAPIClient: APIClient {
7171
completion: CompletionCallback<T>
7272
) {
7373
switch result {
74-
case .success(let response): handle(response, with: endpoint.decodingConfiguration, completion: completion)
75-
case .failure(let error): completion(.failure(error), [:])
74+
case .success(let response):
75+
handle(response, with: endpoint.decodingConfiguration, completion: completion)
76+
case .failure(let error):
77+
completion(.failure(error), [:])
7678
}
7779
}
7880

@@ -94,7 +96,9 @@ internal final class BaseAPIClient: APIClient {
9496
) {
9597
do {
9698
guard let data = response.data, !data.isEmpty else {
97-
guard emptyDataStatusCodes.contains(response.statusCode) else { throw unexpectedResponseError }
99+
guard emptyDataStatusCodes.contains(response.statusCode) else {
100+
throw unexpectedResponseError
101+
}
98102

99103
return completion(.success(.none), response.headers)
100104
}
@@ -108,7 +112,10 @@ internal final class BaseAPIClient: APIClient {
108112
}
109113
}
110114

111-
private func decode<M: Decodable>(_ data: Data, with configuration: DecodingConfiguration?) throws -> M {
115+
private func decode<M: Decodable>(
116+
_ data: Data,
117+
with configuration: DecodingConfiguration?
118+
) throws -> M {
112119
let decoder = JSONDecoder(decodingConfig: configuration ?? decodingConfiguration)
113120

114121
return try decoder.decode(M.self, from: data)

ios-base/Onboarding/Routes/OnboardingRoutes.swift

Lines changed: 3 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -26,24 +26,17 @@ enum OnboardingRoutes: Route {
2626
}
2727

2828
private func buildSignInViewController() -> UIViewController {
29-
guard let signIn = R.storyboard.main.signInViewController() else {
30-
return UIViewController()
31-
}
32-
signIn.viewModel = SignInViewModelWithCredentials()
29+
let signIn = SignInViewController(viewModel: SignInViewModelWithCredentials())
3330
return signIn
3431
}
3532

3633
private func buildSignUpViewController() -> UIViewController {
37-
guard let signUp = R.storyboard.main.signUpViewController() else {
38-
return UIViewController()
39-
}
40-
signUp.viewModel = SignUpViewModelWithEmail()
34+
let signUp = SignUpViewController(viewModel: SignUpViewModelWithEmail())
4135
return signUp
4236
}
4337

4438
private func buildFirstViewController() -> UIViewController {
45-
let firstViewController = FirstViewController()
46-
firstViewController.viewModel = FirstViewModel()
39+
let firstViewController = FirstViewController(viewModel: FirstViewModel())
4740
return firstViewController
4841
}
4942
}

0 commit comments

Comments
 (0)