Skip to content

Commit

Permalink
Merge pull request #104 from AckeeCZ/feature/configurable_gradient_view
Browse files Browse the repository at this point in the history
  • Loading branch information
olejnjak authored Jan 20, 2021
2 parents 6f61976 + ebf37bc commit 3251792
Show file tree
Hide file tree
Showing 6 changed files with 113 additions and 11 deletions.
41 changes: 30 additions & 11 deletions ACKategories-iOS/GradientView.swift
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,21 @@ open class GradientView: UIView {

// MARK: - Private properties

private var colors: [UIColor]
/// The axis of the gradient: `.vertical` for bottom-to-top gradient, `.horizontal` for left-to-right gradient.
///
/// Default value is `.vertical`
public var axis: NSLayoutConstraint.Axis {
didSet {
setupAxis()
}
}

/// The colors to be used for the gradient
public var colors: [UIColor] {
didSet {
setupGradientColors()
}
}

// MARK: - Initializers

Expand All @@ -29,24 +43,18 @@ open class GradientView: UIView {
- colors: The colors to be used for the gradient.
- axis: The axis of the gradient: `.vertical` for bottom-to-top gradient, `.horizontal` for left-to-right gradient.
*/
public init(colors: [UIColor], axis: NSLayoutConstraint.Axis) {
public init(colors: [UIColor] = [], axis: NSLayoutConstraint.Axis = .vertical) {
self.axis = axis
self.colors = colors
super.init(frame: CGRect(x: 0, y: 0, width: 1, height: 1))

guard let gradientLayer = layer as? CAGradientLayer else { return }
gradientLayer.frame = bounds

isUserInteractionEnabled = false

gradientLayer.frame = bounds
setupAxis()
setupGradientColors()

if axis == .vertical {
gradientLayer.startPoint = CGPoint(x: 0.5, y: 0)
gradientLayer.endPoint = CGPoint(x: 0.5, y: 1)
} else {
gradientLayer.startPoint = CGPoint(x: 0.0, y: 0.5)
gradientLayer.endPoint = CGPoint(x: 1.0, y: 0.5)
}
}

required public init?(coder aDecoder: NSCoder) {
Expand All @@ -67,4 +75,15 @@ open class GradientView: UIView {
guard let gradientLayer = layer as? CAGradientLayer else { return }
gradientLayer.colors = colors.map { $0.cgColor }
}

private func setupAxis() {
guard let gradientLayer = layer as? CAGradientLayer else { return }
if axis == .vertical {
gradientLayer.startPoint = CGPoint(x: 0.5, y: 0)
gradientLayer.endPoint = CGPoint(x: 0.5, y: 1)
} else {
gradientLayer.startPoint = CGPoint(x: 0.0, y: 0.5)
gradientLayer.endPoint = CGPoint(x: 1.0, y: 0.5)
}
}
}
12 changes: 12 additions & 0 deletions ACKategories.xcodeproj/project.pbxproj
Original file line number Diff line number Diff line change
Expand Up @@ -108,6 +108,7 @@
69FA5FBD23C868A900B44BCD /* ModalFlowCoordinator.swift in Sources */ = {isa = PBXBuildFile; fileRef = 69FA5FAC23C868A900B44BCD /* ModalFlowCoordinator.swift */; };
69FA5FC223C8690A00B44BCD /* LaunchScreen.storyboard in Resources */ = {isa = PBXBuildFile; fileRef = 69FA5FC123C8690A00B44BCD /* LaunchScreen.storyboard */; };
6A31C9F3250572FE0047A983 /* SelfSizingTableHeaderFooterView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6A31C9F2250572FE0047A983 /* SelfSizingTableHeaderFooterView.swift */; };
88EDD90425B8252E00207987 /* GradientViewController.swift in Sources */ = {isa = PBXBuildFile; fileRef = 88EDD90325B8252E00207987 /* GradientViewController.swift */; };
A33559012555270F009B9D89 /* FlowCoordinatorTests.swift in Sources */ = {isa = PBXBuildFile; fileRef = A33559002555270F009B9D89 /* FlowCoordinatorTests.swift */; };
A38883E3257E2D2D00B958DD /* ErrorHandlers.swift in Sources */ = {isa = PBXBuildFile; fileRef = A38883E2257E2D2D00B958DD /* ErrorHandlers.swift */; };
A3BA685B256BEC7B006DB42F /* UIWindow.swift in Sources */ = {isa = PBXBuildFile; fileRef = A3BA685A256BEC7B006DB42F /* UIWindow.swift */; };
Expand Down Expand Up @@ -269,6 +270,7 @@
69FA5FC323C869A200B44BCD /* ACKategories.podspec */ = {isa = PBXFileReference; explicitFileType = text.script.ruby; path = ACKategories.podspec; sourceTree = "<group>"; };
69FA5FE423C8712D00B44BCD /* Package.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = Package.swift; sourceTree = "<group>"; };
6A31C9F2250572FE0047A983 /* SelfSizingTableHeaderFooterView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = SelfSizingTableHeaderFooterView.swift; sourceTree = "<group>"; };
88EDD90325B8252E00207987 /* GradientViewController.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = GradientViewController.swift; sourceTree = "<group>"; };
A33559002555270F009B9D89 /* FlowCoordinatorTests.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = FlowCoordinatorTests.swift; sourceTree = "<group>"; };
A38883E2257E2D2D00B958DD /* ErrorHandlers.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ErrorHandlers.swift; sourceTree = "<group>"; };
A3BA685A256BEC7B006DB42F /* UIWindow.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = UIWindow.swift; sourceTree = "<group>"; };
Expand Down Expand Up @@ -494,6 +496,7 @@
69FA5F9123C868A900B44BCD /* Screens */ = {
isa = PBXGroup;
children = (
88EDD8FD25B824C200207987 /* GradientView */,
69FA5F9223C868A900B44BCD /* UIControl blocks */,
69FA5F9423C868A900B44BCD /* VC composition */,
69FA5F9723C868A900B44BCD /* MapView */,
Expand Down Expand Up @@ -580,6 +583,14 @@
path = "Flow coordinators";
sourceTree = "<group>";
};
88EDD8FD25B824C200207987 /* GradientView */ = {
isa = PBXGroup;
children = (
88EDD90325B8252E00207987 /* GradientViewController.swift */,
);
path = GradientView;
sourceTree = "<group>";
};
A3BA6858256BEC56006DB42F /* FlowCoordinator */ = {
isa = PBXGroup;
children = (
Expand Down Expand Up @@ -919,6 +930,7 @@
files = (
69FA5FBD23C868A900B44BCD /* ModalFlowCoordinator.swift in Sources */,
69FA5FB523C868A900B44BCD /* ModalViewController.swift in Sources */,
88EDD90425B8252E00207987 /* GradientViewController.swift in Sources */,
69FA5FBC23C868A900B44BCD /* AppFlowCoordinator.swift in Sources */,
69FA5FB023C868A900B44BCD /* VCCompositionViewController.swift in Sources */,
69FA5FB223C868A900B44BCD /* MapViewModel.swift in Sources */,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -44,6 +44,10 @@ extension AppFlowCoordinator: ExampleListFlowDelegate {
let mapVC = MapViewController(viewModel: MapViewModel())
mapVC.title = item.title
navigationController?.pushViewController(mapVC, animated: true)
case .gradientView:
let gradientVC = GradientViewController()
gradientVC.title = item.title
navigationController?.pushViewController(gradientVC, animated: true)
}
}
}
2 changes: 2 additions & 0 deletions ACKategoriesExample/Model/ExampleItem.swift
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,7 @@ enum ExampleItem: CaseIterable {
case viewControllerComposition
case mapViewController
case present
case gradientView

var title: String { return data.title }
var subtitle: String { return data.subtitle }
Expand All @@ -23,6 +24,7 @@ enum ExampleItem: CaseIterable {
case .viewControllerComposition: return ("View controller composition", "Simply embed view controller into another one")
case .mapViewController: return ("Map View Controller", "Operations on MKMapView")
case .present: return ("Present", "Example usage of starting flow coordinator with modal present")
case .gradientView: return ("GradientView", "Example usage of gradient view")
}
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,64 @@
//
// GradientViewController.swift
// ACKategoriesExample
//
// Created by Jan Mísař on 20.01.2021.
//

import UIKit
import ACKategories

class GradientViewController: UIViewController {

private weak var gradientView: GradientView!
private weak var button: UIButton!

override func loadView() {
super.loadView()

view.backgroundColor = .white

let gradientView = GradientView()
view.addSubview(gradientView)
gradientView.translatesAutoresizingMaskIntoConstraints = false
NSLayoutConstraint.activate([
gradientView.topAnchor.constraint(equalTo: view.topAnchor),
gradientView.leadingAnchor.constraint(equalTo: view.leadingAnchor),
gradientView.bottomAnchor.constraint(equalTo: view.bottomAnchor),
gradientView.trailingAnchor.constraint(equalTo: view.trailingAnchor)
])
self.gradientView = gradientView

let button = UIButton(type: .system)
button.setTitle("Change colors and switch axis", for: .normal)
button.backgroundColor = .white
button.titleEdgeInsets = UIEdgeInsets(top: 5, left: 10, bottom: 5, right: 10)
view.addSubview(button)
button.translatesAutoresizingMaskIntoConstraints = false
NSLayoutConstraint.activate([
button.centerXAnchor.constraint(equalTo: view.centerXAnchor),
button.centerYAnchor.constraint(equalTo: view.centerYAnchor)
])
self.button = button
}

override func viewDidLoad() {
super.viewDidLoad()

button.on(.touchUpInside) { [unowned self] _ in
self.gradientView.colors = GradientViewController.randomColors()
self.gradientView.axis = (self.gradientView.axis == .vertical) ? .horizontal : .vertical
}
}

private static func randomColors() -> [UIColor] {
let colorsCount = Int.random(in: 2..<5)

var colors = [UIColor]()
(0..<colorsCount).forEach { _ in
colors.append(UIColor.random())
}
return colors
}

}
1 change: 1 addition & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@
### Added

- Add completion blocks to `UINavigationController` pop and push methods ([#101](https://github.com/AckeeCZ/ACKategories/pull/101), kudos to @olejnjak)
- Add possibility to configure GradientView with public properties `colors` and `axis` even after init ([#104](https://github.com/AckeeCZ/ACKategories/pull/104), kudos to @janmisar)

## 6.7.4

Expand Down

0 comments on commit 3251792

Please sign in to comment.