Compare commits

...

6 Commits

Author SHA1 Message Date
Ivan Vorobei a1d17d994c Update to 1.4
If tap on `indicatorView`, controller will be close as in app Apple Music by Apple
2019-02-04 20:41:20 +03:00
Ivan Vorobei f56a054b91 Update SPStorkController.podspec 2019-02-04 01:41:40 +03:00
Ivan Vorobei bd26c4d721 Update SPStorkController.podspec 2019-02-04 01:39:58 +03:00
Ivan Vorobei 6927d90572 Update SPStorkController.podspec 2019-02-04 01:37:03 +03:00
Ivan Vorobei ea32992f63 Update to 1.2.8 2019-02-04 01:34:25 +03:00
Ivan Vorobei 05ba026c1f Update to 1.2.6
Add extenshion to UIViewController. Property `isPresentedAsStork` check if currenct controller present with this pod. For simple usage add func `presentAsStork` - need pass controller only.
2019-02-04 01:20:29 +03:00
117 changed files with 1249 additions and 1259 deletions
File diff suppressed because it is too large Load Diff
@@ -63,12 +63,3 @@ public struct SPStorkController {
private init() {}
}
extension UIViewController {
var isPresentedAsStork: Bool {
return transitioningDelegate is SPStorkTransitioningDelegate
&& modalPresentationStyle == .custom
&& presentingViewController != nil
}
}
@@ -84,6 +84,9 @@ class SPStorkPresentationController: UIPresentationController, UIGestureRecogniz
if self.showIndicator {
self.indicatorView.color = self.indicatorColor
let tap = UITapGestureRecognizer.init(target: self, action: #selector(self.handleTap))
tap.cancelsTouchesInView = false
self.indicatorView.addGestureRecognizer(tap)
presentedView.addSubview(self.indicatorView)
}
self.updateLayoutIndicator()
@@ -0,0 +1,38 @@
// The MIT License (MIT)
// Copyright © 2017 Ivan Vorobei (hello@ivanvorobei.by)
//
// Permission is hereby granted, free of charge, to any person obtaining a copy
// of this software and associated documentation files (the "Software"), to deal
// in the Software without restriction, including without limitation the rights
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
// copies of the Software, and to permit persons to whom the Software is
// furnished to do so, subject to the following conditions:
//
// The above copyright notice and this permission notice shall be included in all
// copies or substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
// SOFTWARE.
import UIKit
extension UIViewController {
public var isPresentedAsStork: Bool {
return transitioningDelegate is SPStorkTransitioningDelegate
&& modalPresentationStyle == .custom
&& presentingViewController != nil
}
public func presentAsStork(_ controller: UIViewController, complection: (() -> Void)? = nil) {
let transitionDelegate = SPStorkTransitioningDelegate()
controller.transitioningDelegate = transitionDelegate
controller.modalPresentationStyle = .custom
self.present(controller, animated: true, completion: complection)
}
}
@@ -23,7 +23,7 @@ import UIKit
public class SPAnimation {
static func animate(_ duration: TimeInterval,
public static func animate(_ duration: TimeInterval,
animations: (() -> Void)!,
delay: TimeInterval = 0,
options: UIView.AnimationOptions = [],
@@ -40,7 +40,7 @@ public class SPAnimation {
})
}
static func animateWithRepeatition(_ duration: TimeInterval,
public static func animateWithRepeatition(_ duration: TimeInterval,
animations: (() -> Void)!,
delay: TimeInterval = 0,
options: UIView.AnimationOptions = [],
@@ -23,11 +23,11 @@ import UIKit
public class SPAnimationAlpha {
fileprivate static let durationListAnimation: TimeInterval = 0.45
fileprivate static let coefLenthForTransition: CGFloat = 2.8
fileprivate static let delayPerItem: TimeInterval = 0.09
public static let durationListAnimation: TimeInterval = 0.45
public static let coefLenthForTransition: CGFloat = 2.8
public static let delayPerItem: TimeInterval = 0.09
static func hideList(_ duration: TimeInterval = durationListAnimation,
public static func hideList(_ duration: TimeInterval = durationListAnimation,
views: [UIView],
delayPerItem: TimeInterval = delayPerItem,
withComplection completion: (() -> Void)! = {}) {
@@ -51,7 +51,7 @@ public class SPAnimationAlpha {
}
}
static func hideReverseList(_ duration: TimeInterval = durationListAnimation,
public static func hideReverseList(_ duration: TimeInterval = durationListAnimation,
views: [UIView],
delayPerItem: TimeInterval = delayPerItem,
withComplection completion: (() -> Void)! = {}) {
@@ -76,7 +76,7 @@ public class SPAnimationAlpha {
}
}
static func showList(_ duration: TimeInterval = durationListAnimation,
public static func showList(_ duration: TimeInterval = durationListAnimation,
views: [UIView],
delayPerItem: TimeInterval = delayPerItem,
withComplection completion: (() -> Void)! = {}) {
@@ -23,10 +23,10 @@ import UIKit
public class SPAnimationSpring {
fileprivate static let spring: CGFloat = 1
fileprivate static let velocity: CGFloat = 1
public static let spring: CGFloat = 1
public static let velocity: CGFloat = 1
static func animate(_ duration: TimeInterval,
public static func animate(_ duration: TimeInterval,
animations: (() -> Void)!,
delay: TimeInterval = 0,
spring: CGFloat = spring,
@@ -47,7 +47,7 @@ public class SPAnimationSpring {
})
}
static func animateWithRepeatition(_ duration: TimeInterval,
public static func animateWithRepeatition(_ duration: TimeInterval,
animations: (() -> Void)!,
delay: TimeInterval = 0,
spring: CGFloat = spring,
@@ -23,11 +23,11 @@ import UIKit
public class SPAnimationUpward {
fileprivate static let durationListAnimation: TimeInterval = 0.45
fileprivate static let coefLenthForTransition: CGFloat = 2.8
fileprivate static let delayPerItem: TimeInterval = 0.09
public static let durationListAnimation: TimeInterval = 0.45
public static let coefLenthForTransition: CGFloat = 2.8
public static let delayPerItem: TimeInterval = 0.09
static func hide(_ duration: TimeInterval,
public static func hide(_ duration: TimeInterval,
view: UIView,
delay: TimeInterval = 0,
withComplection completion: (() -> Void)! = {}) {
@@ -48,7 +48,7 @@ public class SPAnimationUpward {
})
}
static func hideList(_ duration: TimeInterval = durationListAnimation,
public static func hideList(_ duration: TimeInterval = durationListAnimation,
views: [UIView],
delayPerItem: TimeInterval = delayPerItem,
withComplection completion: (() -> Void)! = {}) {
@@ -69,7 +69,7 @@ public class SPAnimationUpward {
}
static func show(_ duration: TimeInterval,
public static func show(_ duration: TimeInterval,
view: UIView,
delay: TimeInterval = 0,
withComplection completion: (() -> Void)! = {}) {
@@ -93,7 +93,7 @@ public class SPAnimationUpward {
})
}
static func showList(_ duration: TimeInterval = durationListAnimation,
public static func showList(_ duration: TimeInterval = durationListAnimation,
views: [UIView],
delayPerItem: TimeInterval = delayPerItem,
options: UIView.AnimationOptions = [],
@@ -24,19 +24,19 @@ import StoreKit
struct SPApp {
static var udid: String? {
public static var udid: String? {
return UIDevice.current.identifierForVendor?.uuidString
}
static var displayName: String? {
public static var displayName: String? {
return Bundle.main.object(forInfoDictionaryKey: "CFBundleDisplayName") as? String
}
static var rootController: UIViewController? {
public static var rootController: UIViewController? {
return UIApplication.shared.keyWindow?.rootViewController
}
static func set(rootController: UIViewController, animatable: Bool = true) {
public static func set(rootController: UIViewController, animatable: Bool = true) {
rootController.view.frame = UIScreen.main.bounds
@@ -57,7 +57,7 @@ struct SPApp {
}
}
static func set(elementsColor: UIColor) {
public static func set(elementsColor: UIColor) {
UINavigationController.elementsColor = elementsColor
UIAlertController.elementsColor = elementsColor
UITabBarController.elementsColor = elementsColor
@@ -25,7 +25,7 @@ extension SPApp {
public struct Badge {
static var number: Int {
public static var number: Int {
get {
return UIApplication.shared.applicationIconBadgeNumber
}
@@ -34,7 +34,7 @@ extension SPApp {
}
}
static func reset() {
public static func reset() {
UIApplication.shared.applicationIconBadgeNumber = 0
}
@@ -23,13 +23,13 @@ import UIKit
extension SPApp {
struct Launch {
public struct Launch {
static func run() {
public static func run() {
self.count += 1
}
static var count: Int {
public static var count: Int {
get {
return UserDefaults.standard.value(forKey: "SPLaunchCount") as? Int ?? 0
}
@@ -38,7 +38,7 @@ extension SPApp {
}
}
static var isFirstLaunch: Bool {
public static var isFirstLaunch: Bool {
return (self.count == 1) || (self.count == 0)
}
@@ -24,7 +24,7 @@ import SafariServices
extension SPApp {
static func open(app: SPSystemApp) {
public static func open(app: SPSystemApp) {
switch app {
case SPSystemApp.photos:
guard let settingsUrl = URL(string: "photos-redirect://") else {
@@ -63,7 +63,7 @@ extension SPApp {
}
}
static func open(link: String, redirect: Bool) {
public static func open(link: String, redirect: Bool) {
guard let url = URL(string: link) else {
print("SPOpener - can not create URL")
@@ -24,11 +24,11 @@ import StoreKit
struct SPAppStore {
static func link(appID: String) -> String {
public static func link(appID: String) -> String {
return "https://itunes.apple.com/by/app/id" + appID
}
static func open(appID: String) {
public static func open(appID: String) {
if let url = URL(string: "itms-apps://itunes.apple.com/app/id\(appID)"),
UIApplication.shared.canOpenURL(url) {
if #available(iOS 10.0, *) {
@@ -39,7 +39,7 @@ struct SPAppStore {
}
}
static func requestReview(appID: String, force: Bool) {
public static func requestReview(appID: String, force: Bool) {
if force {
if let url = URL(string: "itms-apps://itunes.apple.com/us/app/apple-store/id\(appID)?mt=8&action=write-review"),
UIApplication.shared.canOpenURL(url) {
@@ -56,13 +56,13 @@ struct SPAppStore {
}
}
static func requestReview() {
public static func requestReview() {
if #available(iOS 10.3, *) {
SKStoreReviewController.requestReview()
}
}
static func isUpdateAvailable(completion: @escaping (Bool)->()) {
public static func isUpdateAvailable(completion: @escaping (Bool)->()) {
guard let info = Bundle.main.infoDictionary,
let currentVersion = info["CFBundleShortVersionString"] as? String,
@@ -24,7 +24,7 @@ import AVFoundation
public struct SPAudio {
static func notStopBackgroundMusic() {
public static func notStopBackgroundMusic() {
do {
try AVAudioSession.sharedInstance().setCategory(AVAudioSession.Category(rawValue: convertFromAVAudioSessionCategory(AVAudioSession.Category.ambient)), mode: AVAudioSession.Mode.default)
try AVAudioSession.sharedInstance().setActive(true)
@@ -27,7 +27,7 @@ public class SPAudioPlayer: NSObject, AVAudioPlayerDelegate {
fileprivate var player: AVAudioPlayer = AVAudioPlayer()
fileprivate var endPlayingComplection: (()->())? = nil
func play(fileName: String, complection: (()->())? = nil) {
public func play(fileName: String, complection: (()->())? = nil) {
self.endPlayingComplection?()
self.player = AVAudioPlayer()
let url = Bundle.main.url(forResource: fileName, withExtension: nil)
@@ -47,7 +47,7 @@ public class SPAudioPlayer: NSObject, AVAudioPlayerDelegate {
}
}
func stop() {
public func stop() {
player.stop()
}
@@ -23,7 +23,7 @@ import UIKit
struct SPBufer {
static var text: String? {
public static var text: String? {
get {
return UIPasteboard.general.string
}
@@ -21,4 +21,4 @@
import UIKit
struct SPCodeDraw { private init() {} }
public struct SPCodeDraw { private init() {} }
@@ -23,7 +23,7 @@ import UIKit
public struct SPConstraints {
static func setEqualSizeSuperview(for view: UIView) {
public static func setEqualSizeSuperview(for view: UIView) {
if let superView = view.superview {
view.translatesAutoresizingMaskIntoConstraints = false
NSLayoutConstraint.activate([
@@ -21,7 +21,7 @@
import Foundation
public func delay(_ delay:Double, closure:@escaping ()->()) {
public func delay(_ delay:Double, closure: @escaping ()->()) {
let when = DispatchTime.now() + delay
DispatchQueue.main.asyncAfter(deadline: when) {
closure()
@@ -21,19 +21,19 @@
import UIKit
struct SPDevice {
public struct SPDevice {
static var iphone: Bool {
public static var iphone: Bool {
return UIDevice.current.userInterfaceIdiom == .phone
}
static var ipad: Bool {
public static var ipad: Bool {
return UIDevice.current.userInterfaceIdiom == .pad
}
struct Orientation {
public struct Orientation {
static var isPortrait: Bool {
public static var isPortrait: Bool {
var isPortraitOrientation = true
if UIDevice.current.orientation.isValidInterfaceOrientation {
if UIDevice.current.orientation.isPortrait {
@@ -23,7 +23,7 @@ import UIKit
struct SPDownloader {
static func image(link: String, withComplection complection: @escaping (UIImage?) -> ()) {
public static func image(link: String, withComplection complection: @escaping (UIImage?) -> ()) {
guard let url = URL(string: link) else {
DispatchQueue.main.async {
complection(nil)
@@ -23,7 +23,7 @@ import Foundation
extension Array {
func get(count: Int) -> Array {
public func get(count: Int) -> Array {
if (count < self.count) { return Array(self[0..<count]) }
return Array(self)
}
@@ -31,7 +31,7 @@ extension Array {
extension Array where Element: Equatable {
mutating func removeDuplicates() {
public mutating func removeDuplicates() {
var result = [Element]()
for value in self {
if result.contains(value) == false { result.append(value) }
@@ -42,7 +42,7 @@ extension Array where Element: Equatable {
extension Array where Element: Hashable {
func after(item: Element) -> Element? {
public func after(item: Element) -> Element? {
if let index = self.index(of: item), index + 1 < self.count { return self[index + 1] }
return nil
}
@@ -23,17 +23,17 @@ import UIKit
extension CGRect {
var bottomXPosition: CGFloat {
public var bottomXPosition: CGFloat {
get { return self.origin.x + self.width }
set { self.origin.x = newValue - self.width }
}
var bottomYPosition: CGFloat {
public var bottomYPosition: CGFloat {
get { return self.origin.y + self.height }
set { self.origin.y = newValue - self.height }
}
var minSideSize: CGFloat {
public var minSideSize: CGFloat {
return min(self.width, self.height)
}
}
@@ -23,13 +23,13 @@ import UIKit
extension CGSize {
func resize(width: CGFloat) -> CGSize {
public func resize(width: CGFloat) -> CGSize {
let relativeSideSize = self.width / self.height
let newHeight = width / relativeSideSize
return CGSize.init(width: width, height: newHeight)
}
func resize(height: CGFloat) -> CGSize {
public func resize(height: CGFloat) -> CGSize {
let relativeSideSize = self.width / self.height
let newWidth = height * relativeSideSize
return CGSize.init(width: newWidth, height: height)
@@ -23,13 +23,13 @@ import Foundation
extension Date {
func format(mask: String) -> String {
public func format(mask: String) -> String {
let dateFormatter = DateFormatter()
dateFormatter.dateFormat = mask
return dateFormatter.string(from: self)
}
static func create(from value: String) -> Date? {
public static func create(from value: String) -> Date? {
let formatter = DateFormatter()
formatter.dateFormat = "dd.MM.yyyy HH:mm"
let date = formatter.date(from: value)
@@ -24,57 +24,57 @@ import UIKit
extension String {
var digits: String {
public var digits: String {
return components(separatedBy: CharacterSet.decimalDigits.inverted).joined()
}
mutating func dropLast(substring: String) {
public mutating func dropLast(substring: String) {
if self.hasSuffix(substring) {
self = String(dropLast(substring.count))
}
}
mutating func dropFirst(substring: String) {
public mutating func dropFirst(substring: String) {
if self.hasPrefix(substring) {
self = String(dropFirst(substring.count))
}
}
func uppercasedFirstLetter() -> String {
public func uppercasedFirstLetter() -> String {
let lowercaseSctring = self.lowercased()
return lowercaseSctring.prefix(1).uppercased() + lowercaseSctring.dropFirst()
}
mutating func uppercaseFirstLetter() {
public mutating func uppercaseFirstLetter() {
self = self.uppercasedFirstLetter()
}
func removeAllSpaces() -> String {
public func removeAllSpaces() -> String {
return self.components(separatedBy: .whitespaces).joined()
}
mutating func removeAllSpaces() {
public mutating func removeAllSpaces() {
self = self.removeAllSpaces()
}
var isEmail: Bool {
public var isEmail: Bool {
let emailRegEx = "[A-Z0-9a-z._%+-]+@[A-Za-z0-9.-]+\\.[A-Za-z]{2,64}"
let emailTest = NSPredicate(format:"SELF MATCHES %@", emailRegEx)
return emailTest.evaluate(with: self)
}
var isLink: Bool {
public var isLink: Bool {
if let url = URL(string: self) {
return UIApplication.shared.canOpenURL(url)
}
return false
}
mutating func replace(_ replacingString: String, with newString: String) {
public mutating func replace(_ replacingString: String, with newString: String) {
self = self.replacingOccurrences(of: replacingString, with: newString)
}
func replace(_ replacingString: String, with newString: String) -> String {
public func replace(_ replacingString: String, with newString: String) -> String {
return self.replacingOccurrences(of: replacingString, with: newString)
}
}
@@ -23,7 +23,7 @@ import UIKit
extension UITextField {
@IBInspectable var placeholderColor: UIColor? {
@IBInspectable public var placeholderColor: UIColor? {
get {
return self.placeholderColor
}
@@ -23,7 +23,7 @@ import UIKit
extension UIAlertController {
static var elementsColor: UIColor {
public static var elementsColor: UIColor {
get {
return UIView.appearance(whenContainedInInstancesOf: [UIAlertController.self]).tintColor
}
@@ -87,17 +87,24 @@ extension UIAlertController {
extension UIAlertController {
func addAction(title: String, complection: @escaping ()->()) {
public func addAction(title: String, complection: @escaping ()->()) {
let action = UIAlertAction(title: title, style: .default) { (action) in
complection()
}
self.addAction(action)
}
func addDestructiveAction(title: String, complection: @escaping ()->()) {
public func addDestructiveAction(title: String, complection: @escaping ()->()) {
let action = UIAlertAction(title: title, style: .destructive) { (action) in
complection()
}
self.addAction(action)
}
public func addCancelAction(title: String, complection: @escaping ()->() = {}) {
let action = UIAlertAction(title: title, style: .cancel) { (action) in
complection()
}
self.addAction(action)
}
}
@@ -23,7 +23,7 @@ import UIKit
extension UIButton {
typealias UIButtonTargetClosure = () -> ()
public typealias UIButtonTargetClosure = () -> ()
private class ClosureWrapper: NSObject {
let closure: UIButtonTargetClosure
@@ -47,7 +47,7 @@ extension UIButton {
}
}
func target(_ action: @escaping UIButtonTargetClosure) {
public func target(_ action: @escaping UIButtonTargetClosure) {
targetClosure = action
addTarget(self, action: #selector(UIButton.targetAction), for: .touchUpInside)
}
@@ -60,20 +60,20 @@ extension UIButton {
extension UIButton {
func setTitle(_ title: String) {
public func setTitle(_ title: String) {
self.setTitle(title, for: .normal)
}
func setTitleColor(_ color: UIColor) {
public func setTitleColor(_ color: UIColor) {
self.setTitleColor(color, for: .normal)
self.setTitleColor(color.withAlphaComponent(0.7), for: .highlighted)
}
func removeAllTargets() {
public func removeAllTargets() {
self.removeTarget(nil, action: nil, for: .allEvents)
}
func showText(_ text: String, withComplection completion: (() -> Void)! = {}) {
public func showText(_ text: String, withComplection completion: (() -> Void)! = {}) {
let baseText = self.titleLabel?.text ?? " "
SPAnimation.animate(0.2, animations: {
self.titleLabel?.alpha = 0
@@ -97,7 +97,7 @@ extension UIButton {
})
}
func setAnimatableText(_ text: String, withComplection completion: (() -> Void)! = {}) {
public func setAnimatableText(_ text: String, withComplection completion: (() -> Void)! = {}) {
SPAnimation.animate(0.3, animations: {
self.titleLabel?.alpha = 0
}, withComplection: {
@@ -110,7 +110,7 @@ extension UIButton {
})
}
func hideContent(completion: (() -> Void)! = {}) {
public func hideContent(completion: (() -> Void)! = {}) {
SPAnimation.animate(0.2, animations: {
self.titleLabel?.alpha = 0
}, withComplection: {
@@ -118,7 +118,7 @@ extension UIButton {
})
}
func showContent(completion: (() -> Void)! = {}) {
public func showContent(completion: (() -> Void)! = {}) {
SPAnimation.animate(0.2, animations: {
self.titleLabel?.alpha = 1
}, withComplection: {
@@ -23,7 +23,7 @@ import UIKit
extension UICollectionView {
var currentIndexCellPath: IndexPath? {
public var currentIndexCellPath: IndexPath? {
let visibleRect = CGRect(origin: self.contentOffset, size: self.bounds.size)
let visiblePoint = CGPoint.init(x: visibleRect.midX, y: visibleRect.midY)
let visibleIndexPath = self.indexPathForItem(at: visiblePoint)
@@ -23,7 +23,7 @@ import UIKit
public extension UIColor {
convenience init(hex: String) {
public convenience init(hex: String) {
var red: CGFloat = 0.0
var green: CGFloat = 0.0
var blue: CGFloat = 0.0
@@ -23,7 +23,7 @@ import UIKit
public extension UILabel {
func setShadowOffsetForLetters(blurRadius: CGFloat = 0, widthOffset: CGFloat = 0, heightOffset: CGFloat, opacity: CGFloat) {
public func setShadowOffsetForLetters(blurRadius: CGFloat = 0, widthOffset: CGFloat = 0, heightOffset: CGFloat, opacity: CGFloat) {
self.layer.shadowRadius = blurRadius
self.layer.shadowOffset = CGSize(
width: widthOffset,
@@ -32,29 +32,29 @@ public extension UILabel {
self.layer.shadowOpacity = Float(opacity)
}
func setShadowOffsetFactorForLetters(blurRadius: CGFloat = 0, widthOffsetFactor: CGFloat = 0, heightOffsetFactor: CGFloat, opacity: CGFloat) {
public func setShadowOffsetFactorForLetters(blurRadius: CGFloat = 0, widthOffsetFactor: CGFloat = 0, heightOffsetFactor: CGFloat, opacity: CGFloat) {
let widthOffset = widthOffsetFactor * self.frame.width
let heightOffset = heightOffsetFactor * self.frame.height
self.setShadowOffsetForLetters(blurRadius: blurRadius, widthOffset: widthOffset, heightOffset: heightOffset, opacity: opacity)
}
func removeShadowForLetters() {
public func removeShadowForLetters() {
self.setShadowOffsetForLetters(blurRadius: 0, widthOffset: 0, heightOffset: 0, opacity: 0)
}
func setCenteringAlignment() {
public func setCenteringAlignment() {
self.textAlignment = .center
self.baselineAdjustment = .alignCenters
}
func setLettersSpacing(_ value: CGFloat) {
public func setLettersSpacing(_ value: CGFloat) {
if let textString = text {
let attrs: [NSAttributedString.Key : Any] = [.kern: value]
attributedText = NSAttributedString(string: textString, attributes: attrs)
}
}
func setLineSpacing(lineSpacing: CGFloat = 0.0, lineHeightMultiple: CGFloat = 0.0) {
public func setLineSpacing(lineSpacing: CGFloat = 0.0, lineHeightMultiple: CGFloat = 0.0) {
guard let labelText = self.text else { return }
@@ -23,7 +23,7 @@ import UIKit
extension UINavigationController {
static var elementsColor: UIColor {
public static var elementsColor: UIColor {
get {
if UINavigationBar.appearance().tintColor != nil {
return UINavigationBar.appearance().tintColor
@@ -23,7 +23,7 @@ import UIKit
extension UITabBarController {
static var elementsColor: UIColor {
public static var elementsColor: UIColor {
get {
if UITabBar.appearance().tintColor != nil {
return UITabBar.appearance().tintColor
@@ -36,7 +36,7 @@ extension UITabBarController {
}
}
func addTabBarItem(title: String, image: UIImage, selectedImage: UIImage? = nil, controller: UIViewController) {
public func addTabBarItem(title: String, image: UIImage, selectedImage: UIImage? = nil, controller: UIViewController) {
let tabBarItem = UITabBarItem(
title: title,
@@ -23,19 +23,19 @@ import UIKit
extension UITableView {
var isEmpty: Bool {
public var isEmpty: Bool {
return self.lastSectionWithRows == nil
}
func isEmpty(section: Int) -> Bool {
public func isEmpty(section: Int) -> Bool {
return self.numberOfRows(inSection: section) == 0
}
var lastSection: Int {
public var lastSection: Int {
return self.numberOfSections - 1
}
var lastSectionWithRows: Int? {
public var lastSectionWithRows: Int? {
if self.numberOfSections == 0 { return nil }
var section = self.numberOfSections - 1
if section < 0 { return nil }
@@ -46,7 +46,7 @@ extension UITableView {
return nil
}
var firstSectionWithRows: Int? {
public var firstSectionWithRows: Int? {
if self.numberOfSections == 0 { return nil }
var section = 0
if section > self.numberOfSections - 1 { return nil }
@@ -27,7 +27,7 @@ extension UITableViewCell {
return subviews.compactMap { $0 as? UIButton }.first
}
var highlightedColor: UIColor? {
public var highlightedColor: UIColor? {
get {
return self.backgroundView?.backgroundColor
}
@@ -23,7 +23,7 @@ import UIKit
extension UITextField {
var isEmptyText: Bool {
public var isEmptyText: Bool {
get {
if self.text == "" {
return true
@@ -90,7 +90,7 @@ extension UIViewController {
}
}
@objc func image(_ image: UIImage, didFinishSavingWithError error: Error?, contextInfo: UnsafeRawPointer) {
@objc public func image(_ image: UIImage, didFinishSavingWithError error: Error?, contextInfo: UnsafeRawPointer) {
if let _ = error {
self.imageSaved(isSuccses: false)
} else {
@@ -98,14 +98,14 @@ extension UIViewController {
}
}
@objc func imageSaved(isSuccses: Bool) {
@objc public func imageSaved(isSuccses: Bool) {
fatalError("SPUIViewControllerExtenshion - Need ovveride 'imageSaved' func")
}
}
extension UIViewController {
func setPrefersLargeNavigationTitle(_ title: String, smallScreenToSmallBar: Bool = true) {
public func setPrefersLargeNavigationTitle(_ title: String, smallScreenToSmallBar: Bool = true) {
self.navigationItem.title = title
if #available(iOS 11.0, *) {
self.navigationItem.largeTitleDisplayMode = .automatic
@@ -23,7 +23,7 @@ import UIKit
public extension UIView {
var viewController: UIViewController? {
public var viewController: UIViewController? {
get {
if let nextResponder = self.next as? UIViewController { return nextResponder }
else if let nextResponder = self.next as? UIView { return nextResponder.viewController }
@@ -34,7 +34,7 @@ public extension UIView {
public extension UIView {
var safeArea: UIEdgeInsets {
public var safeArea: UIEdgeInsets {
if #available(iOS 11.0, *) {
return self.safeAreaInsets
} else{
@@ -42,24 +42,24 @@ public extension UIView {
}
}
func set(width: CGFloat, height: CGFloat) {
public func set(width: CGFloat, height: CGFloat) {
self.setHeight(height)
self.setWidth(width)
}
func setHeight(_ height: CGFloat) {
public func setHeight(_ height: CGFloat) {
self.frame = CGRect.init(x: self.frame.origin.x, y: self.frame.origin.y, width: self.frame.width, height: height)
}
func setWidth(_ width: CGFloat) {
public func setWidth(_ width: CGFloat) {
self.frame = CGRect.init(x: self.frame.origin.x, y: self.frame.origin.y, width: width, height: self.frame.height)
}
func setEqualsFrameFromBounds(_ view: UIView, withWidthFactor widthFactor: CGFloat = 1, maxWidth: CGFloat? = nil, withHeightFactor heightFactor: CGFloat = 1, maxHeight: CGFloat? = nil, withCentering: Bool = false) {
public func setEqualsFrameFromBounds(_ view: UIView, withWidthFactor widthFactor: CGFloat = 1, maxWidth: CGFloat? = nil, withHeightFactor heightFactor: CGFloat = 1, maxHeight: CGFloat? = nil, withCentering: Bool = false) {
self.setEqualsFrameFromBounds(view.bounds, withWidthFactor: widthFactor, maxWidth: maxWidth, withHeightFactor: heightFactor, maxHeight: maxHeight, withCentering: withCentering)
}
func setEqualsFrameFromBounds(_ bounds: CGRect, withWidthFactor widthFactor: CGFloat = 1, maxWidth: CGFloat? = nil, withHeightFactor heightFactor: CGFloat = 1, maxHeight: CGFloat? = nil, withCentering: Bool = false) {
public func setEqualsFrameFromBounds(_ bounds: CGRect, withWidthFactor widthFactor: CGFloat = 1, maxWidth: CGFloat? = nil, withHeightFactor heightFactor: CGFloat = 1, maxHeight: CGFloat? = nil, withCentering: Bool = false) {
var width = bounds.width * widthFactor
if maxWidth != nil { width.setIfMore(when: maxWidth!) }
@@ -75,7 +75,7 @@ public extension UIView {
}
}
func setEqualsBoundsFromSuperview(customWidth: CGFloat? = nil, customHeight: CGFloat? = nil) {
public func setEqualsBoundsFromSuperview(customWidth: CGFloat? = nil, customHeight: CGFloat? = nil) {
if self.superview == nil { return }
self.frame = CGRect.init(origin: CGPoint.zero, size: self.superview!.frame.size)
if customWidth != nil {
@@ -86,7 +86,7 @@ public extension UIView {
}
}
func resize(width: CGFloat) {
public func resize(width: CGFloat) {
let relativeFactor = self.frame.width / self.frame.height
if relativeFactor.isNaN { return }
self.frame = CGRect.init(
@@ -97,7 +97,7 @@ public extension UIView {
)
}
func resize(height: CGFloat) {
public func resize(height: CGFloat) {
let relativeFactor = self.frame.width / self.frame.height
if relativeFactor.isNaN { return }
self.frame = CGRect.init(
@@ -108,27 +108,27 @@ public extension UIView {
)
}
func setYCenteringFromSuperview() {
public func setYCenteringFromSuperview() {
self.center.y = (self.superview?.frame.height ?? 0) / 2
}
func setXCenteringFromSuperview() {
public func setXCenteringFromSuperview() {
self.center.x = (self.superview?.frame.width ?? 0) / 2
}
func setToCenterInSuperview() {
public func setToCenterInSuperview() {
self.center = CGPoint.init(x: ((self.superview?.frame.width) ?? 0) / 2, y: ((self.superview?.frame.height) ?? 0) / 2)
}
}
public extension UIView {
func setParalax(amountFactor: CGFloat) {
public func setParalax(amountFactor: CGFloat) {
let amount = self.frame.minSideSize * amountFactor
self.setParalax(amount: amount)
}
func setParalax(amount: CGFloat) {
public func setParalax(amount: CGFloat) {
self.motionEffects.removeAll()
let horizontal = UIInterpolatingMotionEffect(keyPath: "center.x", type: .tiltAlongHorizontalAxis)
horizontal.minimumRelativeValue = -amount
@@ -146,7 +146,7 @@ public extension UIView {
public extension UIView {
func addGrade(alpha: CGFloat, color: UIColor = UIColor.black) -> UIView {
public func addGrade(alpha: CGFloat, color: UIColor = UIColor.black) -> UIView {
let gradeView = UIView.init()
gradeView.alpha = 0
self.addSubview(gradeView)
@@ -159,7 +159,7 @@ public extension UIView {
extension UIView {
func setShadow(
public func setShadow(
xTranslationFactor: CGFloat,
yTranslationFactor: CGFloat,
widthRelativeFactor: CGFloat,
@@ -191,7 +191,7 @@ extension UIView {
self.layer.shadowPath = shadowPath.cgPath;
}
func setShadow(
public func setShadow(
xTranslation: CGFloat,
yTranslation: CGFloat,
widthRelativeFactor: CGFloat,
@@ -216,14 +216,14 @@ extension UIView {
self.layer.shadowPath = shadowPath.cgPath
}
func removeShadow() {
public func removeShadow() {
self.layer.shadowColor = nil
self.layer.shadowOffset = CGSize.zero
self.layer.shadowOpacity = 0
self.layer.shadowPath = nil
}
func addShadowOpacityAnimation(to: CGFloat, duration: CFTimeInterval) {
public func addShadowOpacityAnimation(to: CGFloat, duration: CFTimeInterval) {
let animation = CABasicAnimation(keyPath:"shadowOpacity")
animation.timingFunction = CAMediaTimingFunction(name: CAMediaTimingFunctionName.easeOut)
animation.fromValue = self.layer.cornerRadius
@@ -237,7 +237,7 @@ extension UIView {
extension UIView {
func addCornerRadiusAnimation(to: CGFloat, duration: CFTimeInterval) {
public func addCornerRadiusAnimation(to: CGFloat, duration: CFTimeInterval) {
let animation = CABasicAnimation(keyPath:"cornerRadius")
animation.timingFunction = CAMediaTimingFunction(name: CAMediaTimingFunctionName.easeOut)
animation.fromValue = self.layer.cornerRadius
@@ -247,14 +247,14 @@ extension UIView {
self.layer.cornerRadius = to
}
func show(duration: TimeInterval = 0.3) {
public func show(duration: TimeInterval = 0.3) {
self.isHidden = false
SPAnimation.animate(duration, animations: {
self.alpha = 1
})
}
func hide(duration: TimeInterval = 0.3) {
public func hide(duration: TimeInterval = 0.3) {
SPAnimation.animate(duration, animations: {
self.alpha = 0
}, withComplection: {
@@ -262,21 +262,21 @@ extension UIView {
})
}
func removeAllAnimations() {
public func removeAllAnimations() {
self.layer.removeAllAnimations()
}
}
extension UIView {
func roundCorners(_ corners: UIRectCorner, radius: CGFloat) {
public func roundCorners(_ corners: UIRectCorner, radius: CGFloat) {
let path = UIBezierPath(roundedRect: self.bounds, byRoundingCorners: corners, cornerRadii: CGSize(width: radius, height: radius))
let mask = CAShapeLayer()
mask.path = path.cgPath
self.layer.mask = mask
}
func round() {
public func round() {
self.layer.cornerRadius = self.frame.minSideSize / 2
}
}
@@ -23,12 +23,12 @@ import UIKit
extension UIVisualEffectView {
convenience init(style: UIBlurEffect.Style) {
public convenience init(style: UIBlurEffect.Style) {
let effect = UIBlurEffect(style: style)
self.init(effect: effect)
}
convenience init(vibrancy style: UIBlurEffect.Style) {
public convenience init(vibrancy style: UIBlurEffect.Style) {
let effect = UIBlurEffect(style: style)
let vibrancyEffect = UIVibrancyEffect(blurEffect: effect)
self.init(effect: vibrancyEffect)
@@ -23,15 +23,15 @@ import Foundation
extension UserDefaults {
func set(stringArray array: [String], forKey key: String) {
public func set(stringArray array: [String], forKey key: String) {
self.set(array, forKey: key)
}
func set(boolArray array: [Bool], forKey key: String) {
public func set(boolArray array: [Bool], forKey key: String) {
self.set(array, forKey: key)
}
func boolArray(forKey defaultName: String) -> [Bool] {
public func boolArray(forKey defaultName: String) -> [Bool] {
return UserDefaults.standard.array(forKey: defaultName) as? [Bool] ?? []
}
}
@@ -21,9 +21,9 @@
import UIKit
struct SPLayout {
public struct SPLayout {
static func sizeWith(widthFactor: CGFloat, maxWidth: CGFloat?, heightFactor: CGFloat, maxHeight: CGFloat?, relativeSideFactor: CGFloat?, from size: CGSize) -> CGSize {
public static func sizeWith(widthFactor: CGFloat, maxWidth: CGFloat?, heightFactor: CGFloat, maxHeight: CGFloat?, relativeSideFactor: CGFloat?, from size: CGSize) -> CGSize {
var widthArea = size.width * widthFactor
var heightArea = size.height * heightFactor
@@ -24,7 +24,7 @@ import LocalAuthentication
struct SPLocalAuthentication {
static var isEnable: Bool {
public static var isEnable: Bool {
let context = LAContext()
var error: NSError?
if context.canEvaluatePolicy(.deviceOwnerAuthenticationWithBiometrics, error: &error) {
@@ -38,7 +38,7 @@ struct SPLocalAuthentication {
}
}
static func request(reason: String, complecton: @escaping (Bool)->()) {
public static func request(reason: String, complecton: @escaping (Bool)->()) {
let context = LAContext()
var error: NSError?
if context.canEvaluatePolicy(.deviceOwnerAuthenticationWithBiometrics, error: &error) {
@@ -21,7 +21,7 @@
import UIKit
enum SPLocale: String, CaseIterable {
public enum SPLocale: String, CaseIterable {
case ru = "ru"
case en = "en"
@@ -24,11 +24,11 @@ import MessageUI
struct SPMail {
static var canSendEmail: Bool {
public static var canSendEmail: Bool {
return MFMailComposeViewController.canSendMail()
}
static func openApp(to email: String, subject: String? = nil, body: String? = nil) {
public static func openApp(to email: String, subject: String? = nil, body: String? = nil) {
let parametrs = "mailto:\(email)?subject=\(subject ?? "")&body=\(body ?? "")".addingPercentEncoding(withAllowedCharacters: CharacterSet.urlQueryAllowed)
if parametrs != nil {
@@ -40,7 +40,7 @@ struct SPMail {
}
}
static func dialog(to email: String, subject: String? = nil, body: String? = nil, on viewController: UIViewController) {
public static func dialog(to email: String, subject: String? = nil, body: String? = nil, on viewController: UIViewController) {
let mailVC = MFMailComposeViewController()
mailVC.mailComposeDelegate = SPMailSingltone.sharedInstance
@@ -21,21 +21,21 @@
import UIKit
enum SPNativeColors {
public enum SPNativeColors {
static let red = UIColor.init(hex: "FF3B30")
static let orange = UIColor.init(hex: "FF9500")
static let yellow = UIColor.init(hex: "FFCC00")
static let green = UIColor.init(hex: "4CD964")
static let tealBlue = UIColor.init(hex: "5AC8FA")
static let blue = UIColor.init(hex: "007AFF")
static let purple = UIColor.init(hex: "5856D6")
static let pink = UIColor.init(hex: "FF2D55")
static let white = UIColor.init(hex: "FFFFFF")
static let customGray = UIColor.init(hex: "EFEFF4")
static let lightGray = UIColor.init(hex: "E5E5EA")
static let lightGray2 = UIColor.init(hex: "D1D1D6")
static let midGray = UIColor.init(hex: "C7C7CC")
static let gray = UIColor.init(hex: "8E8E93")
static let black = UIColor.init(hex: "000000")
public static let red = UIColor.init(hex: "FF3B30")
public static let orange = UIColor.init(hex: "FF9500")
public static let yellow = UIColor.init(hex: "FFCC00")
public static let green = UIColor.init(hex: "4CD964")
public static let tealBlue = UIColor.init(hex: "5AC8FA")
public static let blue = UIColor.init(hex: "007AFF")
public static let purple = UIColor.init(hex: "5856D6")
public static let pink = UIColor.init(hex: "FF2D55")
public static let white = UIColor.init(hex: "FFFFFF")
public static let customGray = UIColor.init(hex: "EFEFF4")
public static let lightGray = UIColor.init(hex: "E5E5EA")
public static let lightGray2 = UIColor.init(hex: "D1D1D6")
public static let midGray = UIColor.init(hex: "C7C7CC")
public static let gray = UIColor.init(hex: "8E8E93")
public static let black = UIColor.init(hex: "000000")
}
@@ -22,9 +22,9 @@
import UIKit
import UserNotifications
struct SPLocalNotification {
public struct SPLocalNotification {
static func add(from timeInterval: TimeInterval, body: String, title: String? = nil, identifier: String? = nil) {
public static func add(from timeInterval: TimeInterval, body: String, title: String? = nil, identifier: String? = nil) {
let content = UNMutableNotificationContent()
content.body = body
@@ -50,8 +50,8 @@ struct SPLocalNotification {
}
}
static func add(in date: Date, body: String, title: String? = nil, identifier: String? = nil) {
public static func add(in date: Date, body: String, title: String? = nil, identifier: String? = nil) {
let content = UNMutableNotificationContent()
content.body = body
content.title = title ?? ""
@@ -77,7 +77,7 @@ struct SPLocalNotification {
}
}
static func remove(identifier: String) {
public static func remove(identifier: String) {
let center = UNUserNotificationCenter.current()
center.removePendingNotificationRequests(withIdentifiers: [identifier])
}
@@ -22,6 +22,7 @@
import UIKit
public extension String {
public static func random(count: Int) -> String {
let strings = [
"В доме кардинала от меня не было тайн; не раз видел я, как он усердно перелистывает старинные книги и жадно роется в пыли фамильных рукописей. Когда я как-то упрекнул его за бесполезные бессонные ночи, после которых он впадал в болезненное уныние, он взглянул на меня с горькой улыбкой и раскрыл передо мною историю города Рима. В этой книге, в двадцатой главе жизнеописания папы Александра Шестого, я прочел следующие строки, навсегда оставшиеся в моей памяти",
@@ -34,6 +35,7 @@ public extension String {
}
public extension Int {
public static func random(_ n: Int) -> Int {
return Int(arc4random_uniform(UInt32(n)))
}
@@ -44,6 +46,7 @@ public extension Int {
}
public extension Double {
public static func random() -> Double {
return Double(arc4random()) / 0xFFFFFFFF
}
@@ -54,6 +57,7 @@ public extension Double {
}
public extension Float {
public static func random() -> Float {
return Float(arc4random()) / 0xFFFFFFFF
}
@@ -64,6 +68,7 @@ public extension Float {
}
public extension CGFloat {
public static func random() -> CGFloat {
return CGFloat(Float(arc4random()) / 0xFFFFFFFF)
}
@@ -75,7 +80,7 @@ public extension CGFloat {
public extension Collection {
func shuffle() -> [Iterator.Element] {
public func shuffle() -> [Iterator.Element] {
var list = Array(self)
list.shuffleInPlace()
return list
@@ -84,7 +89,7 @@ public extension Collection {
extension Collection where Index == Int {
func random() -> Iterator.Element? {
public func random() -> Iterator.Element? {
return isEmpty ? nil : self[Int(arc4random_uniform(UInt32(endIndex)))]
}
}
@@ -21,4 +21,4 @@
import Foundation
struct SPShadow { private init() {} }
public struct SPShadow { private init() {} }
@@ -23,7 +23,7 @@ import UIKit
extension SPShadow {
struct DeepStyle {
public struct DeepStyle {
private init() {}
@@ -85,14 +85,14 @@ extension SPShadow {
extension UIView {
func setDeepShadow() {
public func setDeepShadow() {
SPShadow.DeepStyle.setFor(view: self)
}
}
extension UILabel {
func setDeepShadowForLetters() {
public func setDeepShadowForLetters() {
SPShadow.DeepStyle.setFor(label: self)
}
}
@@ -25,7 +25,7 @@ public struct SPShare {
public struct Native {
static func share(text: String? = nil, fileNames: [String] = [], images: [UIImage] = [], complection: ((_ isSharing: Bool)->())? = nil, sourceView: UIView, on viewController: UIViewController) {
public static func share(text: String? = nil, fileNames: [String] = [], images: [UIImage] = [], complection: ((_ isSharing: Bool)->())? = nil, sourceView: UIView, on viewController: UIViewController) {
var shareData: [Any] = []
if text != nil {
@@ -21,13 +21,13 @@
import UIKit
class SPInstagram {
public class SPInstagram {
static var isSetApp: Bool {
public static var isSetApp: Bool {
return UIApplication.shared.canOpenURL(URL(string: "instagram://user?username=test")!)
}
static func openPost(id: String) {
public static func openPost(id: String) {
let instagramHooks = "instagram://media?id=\(id)"
let instagramUrl = URL(string: instagramHooks)
let safariURL = URL(string: "instagram.com/\(id)")!
@@ -38,7 +38,7 @@ class SPInstagram {
}
}
static func openUser(username: String) {
public static func openUser(username: String) {
let instagramHooks = "instagram://user?username=\(username)"
let instagramUrl = URL(string: instagramHooks)
let safariURL = URL(string: "https://instagram.com/\(username)")!
@@ -21,13 +21,13 @@
import UIKit
class SPTelegram {
public class SPTelegram {
static var isSetApp: Bool {
public static var isSetApp: Bool {
return UIApplication.shared.canOpenURL(URL(string: "tg://msg?text=test")!)
}
static func share(text: String, complection: @escaping (_ isOpened: Bool)->() = {_ in }) {
public static func share(text: String, complection: @escaping (_ isOpened: Bool)->() = {_ in }) {
let urlStringEncoded = text.addingPercentEncoding( withAllowedCharacters: .urlHostAllowed)
let urlOptional = URL(string: "tg://msg?text=\(urlStringEncoded ?? "")")
if let url = urlOptional {
@@ -41,12 +41,12 @@ class SPTelegram {
}
}
static func joinChannel(id: String) {
public static func joinChannel(id: String) {
let url = "https://t.me/joinchat/\(id)"
SPApp.open(link: url, redirect: true)
}
static func openBot(username: String) {
public static func openBot(username: String) {
var username = username
if username.first == "@" {
username.removeFirst()
@@ -21,13 +21,13 @@
import UIKit
class SPTwitter {
public class SPTwitter {
static var isSetApp: Bool {
public static var isSetApp: Bool {
return UIApplication.shared.canOpenURL(URL(string: "twitter://post?message=test")!)
}
static func share(text: String, complection: @escaping (_ isOpened: Bool)->() = {_ in }) {
public static func share(text: String, complection: @escaping (_ isOpened: Bool)->() = {_ in }) {
let urlStringEncoded = text.addingPercentEncoding( withAllowedCharacters: .urlHostAllowed)
let urlOptional = URL(string: "twitter://post?message=\(urlStringEncoded ?? "")")
if let url = urlOptional {
@@ -21,13 +21,13 @@
import UIKit
class SPViber {
public class SPViber {
static var isSetApp: Bool {
public static var isSetApp: Bool {
return UIApplication.shared.canOpenURL(URL(string: "viber://forward?text=test")!)
}
static func share(text: String, complection: @escaping (_ isOpened: Bool)->() = {_ in }) {
public static func share(text: String, complection: @escaping (_ isOpened: Bool)->() = {_ in }) {
let urlStringEncoded = text.addingPercentEncoding( withAllowedCharacters: .urlHostAllowed)
let urlOptional = URL(string: "viber://forward?text=\(urlStringEncoded ?? "")")
if let url = urlOptional {
@@ -21,13 +21,13 @@
import UIKit
class SPWhatsApp {
public class SPWhatsApp {
static var isSetApp: Bool {
public static var isSetApp: Bool {
return UIApplication.shared.canOpenURL(URL(string: "whatsapp://send?text=test")!)
}
static func share(text: String, complection: @escaping (_ isOpened: Bool)->() = {_ in }) {
public static func share(text: String, complection: @escaping (_ isOpened: Bool)->() = {_ in }) {
let urlStringEncoded = text.addingPercentEncoding( withAllowedCharacters: .urlHostAllowed)
let urlOptional = URL(string: "whatsapp://send?text=\(urlStringEncoded ?? "")")
if let url = urlOptional {
@@ -1,62 +0,0 @@
// The MIT License (MIT)
// Copyright © 2017 Ivan Vorobei (hello@ivanvorobei.by)
//
// Permission is hereby granted, free of charge, to any person obtaining a copy
// of this software and associated documentation files (the "Software"), to deal
// in the Software without restriction, including without limitation the rights
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
// copies of the Software, and to permit persons to whom the Software is
// furnished to do so, subject to the following conditions:
//
// The above copyright notice and this permission notice shall be included in all
// copies or substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
// SOFTWARE.
import Foundation
import CoreSpotlight
import MobileCoreServices
struct SPSpotlight {
static let domainIdentifier = "by.ivanvorobei"
static func addItem(identifier: String, title: String, description: String, addedData: Date? = nil, keywords: [String] = []) {
if #available(iOS 9.0, *) {
let attributeSet = CSSearchableItemAttributeSet(itemContentType: kUTTypeMessage as String)
attributeSet.title = title
attributeSet.contentDescription = description
attributeSet.keywords = keywords
if addedData != nil {
attributeSet.contentCreationDate = addedData!
}
let item = CSSearchableItem(uniqueIdentifier: "\(identifier)", domainIdentifier: SPSpotlight.domainIdentifier, attributeSet: attributeSet)
CSSearchableIndex.default().indexSearchableItems([item]) { error in
if let error = error {
print("SPSpotlight addItem error: \(error.localizedDescription)")
}
}
}
}
static func removeItem(identifier: String) {
if #available(iOS 9.0, *) {
CSSearchableIndex.default().deleteSearchableItems(withIdentifiers: ["\(identifier)"]) { error in
if let error = error {
print("SPSpotlight removeItem error: \(error.localizedDescription)")
}
}
}
}
private init() {}
}
@@ -21,7 +21,7 @@
import UIKit
class SPAppStoreActionButton: SPDownloadingButton {
public class SPAppStoreActionButton: SPDownloadingButton {
var style: Style = .base {
didSet {
@@ -78,7 +78,7 @@ class SPAppStoreActionButton: SPDownloadingButton {
self.layer.masksToBounds = true
}
override func setTitle(_ title: String?, for state: UIControl.State) {
override public func setTitle(_ title: String?, for state: UIControl.State) {
switch self.style {
case .base:
super.setTitle(title?.uppercased(), for: state)
@@ -91,7 +91,7 @@ class SPAppStoreActionButton: SPDownloadingButton {
}
}
override func layoutSubviews() {
override public func layoutSubviews() {
super.layoutSubviews()
if self.style == .buyInStore {
self.layer.cornerRadius = 12
@@ -21,7 +21,7 @@
import UIKit
class SPAppleMusicButton: SPButton {
public class SPAppleMusicButton: SPButton {
var type: SPSelectionType = .unselect {
didSet {
@@ -21,7 +21,7 @@
import UIKit
class SPAppleMusicSectionButtonsView: SPView {
public class SPAppleMusicSectionButtonsView: SPView {
let topSeparatorView = SPSeparatorView()
let bottomSeparatorView = SPSeparatorView()
@@ -68,7 +68,7 @@ class SPAppleMusicSectionButtonsView: SPView {
self.layoutSubviews()
}
override func layoutSubviews() {
override public func layoutSubviews() {
super.layoutSubviews()
self.topSeparatorView.frame.origin = .zero
@@ -21,7 +21,7 @@
import UIKit
class SPDotButton: SPButton {
public class SPDotButton: SPButton {
var customSideSize: CGFloat = 26 {
didSet {
@@ -37,7 +37,7 @@ class SPDotButton: SPButton {
}
}
override var isHighlighted: Bool{
override public var isHighlighted: Bool{
didSet{
if isHighlighted{
UIView.animate(withDuration: 0.1, delay: 0.0, usingSpringWithDamping: 1, initialSpringVelocity: 1.0, options: [.curveEaseOut, .beginFromCurrentState], animations: {
@@ -69,14 +69,14 @@ class SPDotButton: SPButton {
}
}
override func sizeToFit() {
override public func sizeToFit() {
super.sizeToFit()
self.setWidth(self.customSideSize)
self.setHeight(self.customSideSize)
self.layoutSubviews()
}
override func layoutSubviews() {
override public func layoutSubviews() {
super.layoutSubviews()
let space: CGFloat = 2
@@ -21,12 +21,11 @@
import UIKit
class SPDownloadingButton: SPButton {
public class SPDownloadingButton: SPButton {
let activityIndicatorView = UIActivityIndicatorView.init()
var isFrameRounded: Bool = false
func startLoading() {
public func startLoading() {
self.activityIndicatorView.alpha = 0
self.activityIndicatorView.isHidden = false
self.activityIndicatorView.startAnimating()
@@ -39,7 +38,10 @@ class SPDownloadingButton: SPButton {
})
}
func stopLoading() {
public func stopLoading(newText: String? = nil) {
if let newText = newText {
self.setTitle(newText)
}
SPAnimation.animate(0.2, animations: {
self.activityIndicatorView.alpha = 0
}, withComplection: {
@@ -50,13 +52,9 @@ class SPDownloadingButton: SPButton {
})
}
override func layoutSubviews() {
override public func layoutSubviews() {
super.layoutSubviews()
self.activityIndicatorView.center = CGPoint.init(x: self.frame.width / 2, y: self.frame.height / 2)
if self.isFrameRounded {
self.round()
}
}
}
@@ -21,9 +21,9 @@
import UIKit
class SPNativeLargeButton: SPDownloadingButton {
public class SPNativeLargeButton: SPDownloadingButton {
override var isHighlighted: Bool {
override public var isHighlighted: Bool {
didSet {
if self.gradientView == nil {
if isHighlighted {
@@ -42,7 +42,7 @@ class SPNativeLargeButton: SPDownloadingButton {
}
}
override func commonInit() {
override public func commonInit() {
super.commonInit()
self.titleLabel?.font = UIFont.system(type: UIFont.BoldType.DemiBold, size: 16)
self.setTitleColor(UIColor.white)
@@ -52,7 +52,7 @@ class SPNativeLargeButton: SPDownloadingButton {
self.contentEdgeInsets = UIEdgeInsets.init(top: 15, left: 15, bottom: 15, right: 15)
}
override func sizeToFit() {
override public func sizeToFit() {
super.sizeToFit()
if let superview = self.superview {
let sideSpace: CGFloat = superview.frame.width * 0.112
@@ -62,7 +62,7 @@ class SPNativeLargeButton: SPDownloadingButton {
}
}
override func layoutSubviews() {
override public func layoutSubviews() {
super.layoutSubviews()
self.gradientView?.setEqualsBoundsFromSuperview()
self.gradientView?.layer.cornerRadius = self.layer.cornerRadius
@@ -21,7 +21,7 @@
import UIKit
class SPPlayCircleButton: UIButton {
public class SPPlayCircleButton: UIButton {
var audioState: AudioState = AudioState.play {
didSet {
@@ -60,7 +60,7 @@ class SPPlayCircleButton: UIButton {
fatalError("init(coder:) has not been implemented")
}
override func layoutSubviews() {
override public func layoutSubviews() {
super.layoutSubviews()
self.iconView.setEqualsFrameFromBounds(self, withWidthFactor: 0.45, withHeightFactor: 0.45, withCentering: true)
self.round()
@@ -21,7 +21,7 @@
import UIKit
class SPSocialButton: UIButton {
public class SPSocialButton: UIButton {
let iconView = SPSocialIconView.init()
var widthIconFactor: CGFloat = 0.5
@@ -33,7 +33,7 @@ class SPSocialButton: UIButton {
}
}
override var isHighlighted: Bool {
override public var isHighlighted: Bool {
didSet {
if isHighlighted {
self.iconView.color = self.iconView.color.withAlphaComponent(0.7)
@@ -43,7 +43,7 @@ class SPSocialButton: UIButton {
}
}
override var isEnabled: Bool {
override public var isEnabled: Bool {
didSet {
if isEnabled {
self.alpha = 1
@@ -79,7 +79,7 @@ class SPSocialButton: UIButton {
self.iconView.color = SPNativeColors.white
}
override func layoutSubviews() {
override public func layoutSubviews() {
super.layoutSubviews()
self.iconView.setEqualsFrameFromBounds(self, withWidthFactor: self.widthIconFactor, withHeightFactor: self.heightIconFactor, withCentering: true)
self.round()
@@ -21,7 +21,7 @@
import UIKit
class SPSystemIconButton: UIButton {
public class SPSystemIconButton: UIButton {
let iconView = SPSystemIconView.init()
var widthIconFactor: CGFloat = 1
@@ -39,7 +39,7 @@ class SPSystemIconButton: UIButton {
}
}
override var isHighlighted: Bool {
override public var isHighlighted: Bool {
didSet {
if isHighlighted {
self.iconView.color = self.color.withAlphaComponent(0.7)
@@ -72,7 +72,7 @@ class SPSystemIconButton: UIButton {
self.addSubview(self.iconView)
}
override func layoutSubviews() {
override public func layoutSubviews() {
super.layoutSubviews()
self.iconView.setEqualsFrameFromBounds(self, withWidthFactor: self.widthIconFactor, withHeightFactor: self.heightIconFactor, withCentering: true)
}
@@ -21,7 +21,7 @@
import UIKit
class SPMengTransformCollectionViewCell: SPCollectionViewCell {
public class SPMengTransformCollectionViewCell: SPCollectionViewCell {
let backgroundImageView = SPDownloadingImageView()
let titleLabel = UILabel()
@@ -153,7 +153,7 @@ class SPMengTransformCollectionViewCell: SPCollectionViewCell {
contentView.bottomAnchor, constant: -20).isActive = true
}
override func prepareForReuse() {
override public func prepareForReuse() {
super.prepareForReuse()
self.backgroundImageView.image = nil
self.titleLabel.text = ""
@@ -23,7 +23,7 @@ import UIKit
public class SPCollectionView: UICollectionView {
var layout = SPCollectionViewLayout()
let layout = UICollectionViewFlowLayout()
private var cacheImages: [(link: String, image: UIImage)] = []
required public init?(coder aDecoder: NSCoder) {
@@ -31,29 +31,31 @@ public class SPCollectionView: UICollectionView {
commonInit()
}
init(frame: CGRect) {
super.init(frame: frame, collectionViewLayout: self.layout)
commonInit()
init() {
super.init(frame: .zero, collectionViewLayout: self.layout)
self.commonInit()
}
init() {
super.init(frame: CGRect.zero, collectionViewLayout: self.layout)
commonInit()
public override init(frame: CGRect, collectionViewLayout layout: UICollectionViewLayout) {
super.init(frame: frame, collectionViewLayout: self.layout)
self.commonInit()
}
internal func commonInit() {
self.layout.scrollDirection = .vertical
self.backgroundColor = UIColor.clear
self.collectionViewLayout = self.layout
self.decelerationRate = UIScrollView.DecelerationRate.fast
self.delaysContentTouches = false
self.isPagingEnabled = false
self.showsHorizontalScrollIndicator = false
self.showsVerticalScrollIndicator = false
}
func height(rows: Int) -> CGFloat {
return self.layout.itemSize.height * CGFloat(rows) + self.layout.minimumLineSpacing * CGFloat(rows - 1)
}
}
//MARK: - cache
//MARK: - Cache
extension SPCollectionView {
func setCachedImage(link: String, indexPath: IndexPath, on imageView: SPDownloadingImageView, cell: SPCollectionViewCell) {
@@ -21,7 +21,7 @@
import UIKit
struct SPMengTransformCollectionData {
public struct SPMengTransformCollectionData {
var title: String
var subtitle: String
@@ -40,7 +40,7 @@ struct SPMengTransformCollectionData {
}
}
class SPMengTransformCollectionView: SPCollectionView {
public class SPMengTransformCollectionView: SPPageCollectionView {
var data: [SPMengTransformCollectionData] = []
var withParalax: Bool = true
@@ -73,11 +73,11 @@ class SPMengTransformCollectionView: SPCollectionView {
extension SPMengTransformCollectionView: UICollectionViewDataSource {
func collectionView(_ collectionView: UICollectionView, numberOfItemsInSection section: Int) -> Int {
public func collectionView(_ collectionView: UICollectionView, numberOfItemsInSection section: Int) -> Int {
return self.data.count
}
func collectionView(_ collectionView: UICollectionView, cellForItemAt indexPath: IndexPath) -> UICollectionViewCell {
public func collectionView(_ collectionView: UICollectionView, cellForItemAt indexPath: IndexPath) -> UICollectionViewCell {
let data = self.data[indexPath.row]
let cell = collectionView.dequeueReusableCell(withReuseIdentifier: "sectionCell", for: indexPath) as! SPMengTransformCollectionViewCell
cell.currentIndexPath = indexPath
@@ -166,7 +166,7 @@ extension SPMengTransformCollectionView: UICollectionViewDataSource {
extension SPMengTransformCollectionView: UICollectionViewDelegate {
func scrollViewDidScroll(_ scrollView: UIScrollView) {
public func scrollViewDidScroll(_ scrollView: UIScrollView) {
self.updateCells()
}
@@ -0,0 +1,92 @@
// The MIT License (MIT)
// Copyright © 2017 Ivan Vorobei (hello@ivanvorobei.by)
//
// Permission is hereby granted, free of charge, to any person obtaining a copy
// of this software and associated documentation files (the "Software"), to deal
// in the Software without restriction, including without limitation the rights
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
// copies of the Software, and to permit persons to whom the Software is
// furnished to do so, subject to the following conditions:
//
// The above copyright notice and this permission notice shall be included in all
// copies or substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
// SOFTWARE.
import UIKit
public class SPPageCollectionView: UICollectionView {
var layout = SPCollectionViewLayout()
private var cacheImages: [(link: String, image: UIImage)] = []
required public init?(coder aDecoder: NSCoder) {
super.init(coder: aDecoder)
commonInit()
}
init(frame: CGRect) {
super.init(frame: frame, collectionViewLayout: self.layout)
commonInit()
}
init() {
super.init(frame: CGRect.zero, collectionViewLayout: self.layout)
commonInit()
}
internal func commonInit() {
self.layout.scrollDirection = .vertical
self.backgroundColor = UIColor.clear
self.collectionViewLayout = self.layout
self.decelerationRate = UIScrollView.DecelerationRate.fast
self.delaysContentTouches = false
self.isPagingEnabled = false
self.showsHorizontalScrollIndicator = false
self.showsVerticalScrollIndicator = false
}
}
//MARK: - cache
extension SPPageCollectionView {
func setCachedImage(link: String, indexPath: IndexPath, on imageView: SPDownloadingImageView, cell: SPCollectionViewCell) {
if let image = self.fromCahce(link: link) {
imageView.setImage(image: image, animatable: false)
} else {
SPDownloader.image(link: link) { (response) in
if let image = response {
if cell.currentIndexPath == indexPath {
imageView.setImage(image: image, animatable: true)
self.toCache(link: link, image: image)
}
}
}
}
}
func toCache(link: String, image: UIImage?) {
if image == nil {
return
}
if self.fromCahce(link: link) == nil {
self.cacheImages.append((link: link, image: image!))
}
}
func fromCahce(link: String) -> UIImage? {
let cachedData = self.cacheImages.first(where: {
$0.link == link
})
return cachedData?.image
}
}
@@ -21,7 +21,7 @@
import UIKit
class SPNativeTableController: SPTableController {
public class SPNativeTableController: SPTableController {
let labelTableViewCellIdentifier: String = "labelTableViewCellIdentifier"
let textFieldTableViewCellIdentifier: String = "textFieldTableViewCellIdentifier"
@@ -42,7 +42,7 @@ class SPNativeTableController: SPTableController {
private var autoSpaceHeight: CGFloat = 35
override func viewDidLoad() {
override public func viewDidLoad() {
super.viewDidLoad()
self.statusBar = .dark
@@ -81,23 +81,23 @@ class SPNativeTableController: SPTableController {
self.updateLayout(with: self.view.frame.size)
}
override func numberOfSections(in tableView: UITableView) -> Int {
override public func numberOfSections(in tableView: UITableView) -> Int {
return super.numberOfSections(in: tableView)
}
override func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
override public func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
return super.tableView(tableView, numberOfRowsInSection: section)
}
override func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
override public func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
fatalError("SPNativeTableViewController - need ivveride cellForRowAt")
}
override func tableView(_ tableView: UITableView, titleForHeaderInSection section: Int) -> String? {
override public func tableView(_ tableView: UITableView, titleForHeaderInSection section: Int) -> String? {
return nil
}
override func tableView(_ tableView: UITableView, titleForFooterInSection section: Int) -> String? {
override public func tableView(_ tableView: UITableView, titleForFooterInSection section: Int) -> String? {
return nil
}
@@ -159,7 +159,7 @@ class SPNativeTableController: SPTableController {
//MARK: - manage selection
extension SPNativeTableController {
override func tableView(_ tableView: UITableView, shouldHighlightRowAt indexPath: IndexPath) -> Bool {
override public func tableView(_ tableView: UITableView, shouldHighlightRowAt indexPath: IndexPath) -> Bool {
if let _ = tableView.cellForRow(at: indexPath) as? SPFormFeaturedTitleTableViewCell {
return false
@@ -173,7 +173,7 @@ extension SPNativeTableController {
//MARK: - manage spaces
extension SPNativeTableController {
override func tableView(_ tableView: UITableView, viewForHeaderInSection section: Int) -> UIView? {
override public func tableView(_ tableView: UITableView, viewForHeaderInSection section: Int) -> UIView? {
if section == 0 {
return self.showTopInsets ? super.tableView(tableView, viewForHeaderInSection: section) : nil
} else {
@@ -181,7 +181,7 @@ extension SPNativeTableController {
}
}
override func tableView(_ tableView: UITableView, viewForFooterInSection section: Int) -> UIView? {
override public func tableView(_ tableView: UITableView, viewForFooterInSection section: Int) -> UIView? {
if section == self.tableView.lastSection {
return self.showBottomInsets ? super.tableView(tableView, viewForFooterInSection: section) : nil
} else {
@@ -189,7 +189,7 @@ extension SPNativeTableController {
}
}
override func tableView(_ tableView: UITableView, heightForHeaderInSection section: Int) -> CGFloat {
override public func tableView(_ tableView: UITableView, heightForHeaderInSection section: Int) -> CGFloat {
let firstSection = self.tableView.firstSectionWithRows
if section == firstSection {
if self.showTopInsets {
@@ -217,7 +217,7 @@ extension SPNativeTableController {
}
override func tableView(_ tableView: UITableView, heightForFooterInSection section: Int) -> CGFloat {
override public func tableView(_ tableView: UITableView, heightForFooterInSection section: Int) -> CGFloat {
if section == self.tableView.lastSectionWithRows {
if self.showBottomInsets {
if self.autoBottomSpace {
@@ -21,7 +21,7 @@
import UIKit
class SPProposeController: SPController {
public class SPProposeController: SPController {
private let data: Data
internal let areaView = AreaView()
@@ -54,7 +54,7 @@ class SPProposeController: SPController {
fatalError("init(coder:) has not been implemented")
}
override func viewDidLoad() {
override public func viewDidLoad() {
super.viewDidLoad()
self.areaView.isHidden = true
@@ -79,7 +79,7 @@ class SPProposeController: SPController {
self.updateLayout(with: self.view.frame.size)
}
override func viewDidAppear(_ animated: Bool) {
override public func viewDidAppear(_ animated: Bool) {
super.viewDidAppear(animated)
if !self.isPresent {
self.present()
@@ -88,7 +88,7 @@ class SPProposeController: SPController {
}
private func present() {
SPVibration.impact(system: .warning)
SPVibration.impact(.warning)
self.areaView.frame.origin.y = self.view.frame.size.height
self.areaView.isHidden = false
SPAnimationSpring.animate(self.animationDuration, animations: {
@@ -99,7 +99,7 @@ class SPProposeController: SPController {
options: .transitionCurlUp)
}
override func dismiss(animated flag: Bool, completion: (() -> Void)? = nil) {
override public func dismiss(animated flag: Bool, completion: (() -> Void)? = nil) {
let hide = {
self.view.backgroundColor = UIColor.black.withAlphaComponent(0)
@@ -21,11 +21,11 @@
import UIKit
class SPTableController: SPStatusBarManagerTableController {
public class SPTableController: SPStatusBarManagerTableController {
var activityIndicatorView = UIActivityIndicatorView.init()
override func viewDidLoad() {
override public func viewDidLoad() {
super.viewDidLoad()
self.activityIndicatorView.stopAnimating()
@@ -35,7 +35,7 @@ class SPTableController: SPStatusBarManagerTableController {
self.updateLayout(with: self.view.frame.size)
}
override func viewWillTransition(to size: CGSize, with coordinator: UIViewControllerTransitionCoordinator) {
override public func viewWillTransition(to size: CGSize, with coordinator: UIViewControllerTransitionCoordinator) {
super.viewWillTransition(to: size, with: coordinator)
coordinator.animate(alongsideTransition: { (contex) in
self.updateLayout(with: size)
@@ -43,7 +43,7 @@ class SPTableController: SPStatusBarManagerTableController {
}
@available(iOS 11.0, *)
override func viewLayoutMarginsDidChange() {
override public func viewLayoutMarginsDidChange() {
super.viewLayoutMarginsDidChange()
self.updateLayout(with: self.view.frame.size)
}
@@ -21,7 +21,7 @@
import UIKit
class SPSectionLabelsView: SPView {
public class SPSectionLabelsView: SPView {
let titleLabel = SPLabel()
let subtitleLabel = SPLabel()
@@ -53,7 +53,7 @@ class SPSectionLabelsView: SPView {
self.layoutSubviews()
}
override func layoutSubviews() {
override public func layoutSubviews() {
super.layoutSubviews()
self.titleLabel.sizeToFit()
@@ -21,7 +21,7 @@
import UIKit
class SPDownloadingImageView: SPImageView {
public class SPDownloadingImageView: SPImageView {
let activityIndiactorView = UIActivityIndicatorView.init()
let gradeView = UIView.init()
@@ -68,7 +68,7 @@ class SPDownloadingImageView: SPImageView {
self.gradeView.alpha = 1
}
override func layoutSubviews() {
override public func layoutSubviews() {
super.layoutSubviews()
self.gradeView.setEqualsBoundsFromSuperview()
self.activityIndiactorView.center = CGPoint.init(x: self.bounds.midX, y: self.bounds.midY)
@@ -21,7 +21,7 @@
import UIKit
class SPFooterActionsView: SPView {
public class SPFooterActionsView: SPView {
var sectionLabels = SPSectionLabelsView()
private var buttons: [SPFooterActionButton] = []
@@ -47,13 +47,20 @@ class SPFooterActionsView: SPView {
self.addSubview(separator)
}
func button(for id: Int) -> SPFooterActionButton? {
if (self.buttons.count - 1) < id {
return nil
}
return self.buttons[id]
}
func layout(origin: CGPoint, width: CGFloat) {
self.frame.origin = origin
self.setWidth(width)
self.layoutSubviews()
}
override func layoutSubviews() {
override public func layoutSubviews() {
super.layoutSubviews()
self.sectionLabels.layout(origin: CGPoint.zero, width: self.frame.width)
@@ -82,10 +89,30 @@ class SPFooterActionsView: SPView {
class SPFooterActionButton: SPButton {
var rightIconView: UIView? {
willSet {
self.rightIconView?.removeFromSuperview()
}
didSet {
if let view = self.rightIconView {
self.addSubview(view)
self.layoutSubviews()
}
}
}
override func commonInit() {
super.commonInit()
self.setTitleColor(SPNativeColors.blue)
self.titleLabel?.font = UIFont.system(type: .Regular, size: 21)
self.contentHorizontalAlignment = .left
}
override func layoutSubviews() {
super.layoutSubviews()
let sideSize: CGFloat = self.frame.height * 0.36
self.rightIconView?.frame = CGRect.init(x: 0, y: 0, width: sideSize, height: sideSize)
self.rightIconView?.center.y = self.frame.height / 2
self.rightIconView?.frame.bottomXPosition = self.frame.width - sideSize / 3
}
}
@@ -21,7 +21,7 @@
import UIKit
class SPGradeBlurView: UIView {
public class SPGradeBlurView: UIView {
internal var gradeView: UIView = UIView()
internal var blurView: UIView = UIView()
@@ -67,7 +67,7 @@ class SPGradeBlurView: UIView {
self.setBlurRadius(blurRaius)
}
override func layoutSubviews() {
override public func layoutSubviews() {
super.layoutSubviews()
self.gradeView.frame = self.bounds
self.blurView.frame = self.bounds
@@ -21,7 +21,7 @@
import UIKit
class SPImageView: UIImageView {
public class SPImageView: UIImageView {
var round: Bool = false {
didSet {
@@ -21,7 +21,7 @@
import UIKit
class SPScrollView: UIScrollView {
public class SPScrollView: UIScrollView {
init() {
super.init(frame: .zero)
@@ -40,7 +40,7 @@ class SPScrollView: UIScrollView {
self.delaysContentTouches = false
}
override func touchesShouldCancel(in view: UIView) -> Bool {
override public func touchesShouldCancel(in view: UIView) -> Bool {
if view is UIControl
&& !(view is UITextInput)
&& !(view is UISlider)
@@ -21,7 +21,7 @@
import UIKit
class SPTextField: UITextField {
public class SPTextField: UITextField {
public var textInsets = UIEdgeInsets(top: 0, left: 0, bottom: 0, right: 0) {
didSet { setNeedsDisplay() }
@@ -21,26 +21,23 @@
import UIKit
class SPEmptyProposeLabel: UILabel {
class SPTextView: UITextView {
var cursorColor: UIColor = UIColor.blue {
didSet {
self.tintColor = self.cursorColor
}
}
init() {
super.init(frame: CGRect.zero)
super.init(frame: .zero, textContainer: nil)
self.commonInit()
}
init(title: String) {
super.init(frame: CGRect.zero)
self.text = title
self.commonInit()
}
private func commonInit() {
self.setCenteringAlignment()
self.font = UIFont.system(type: .Regular, size: 14)
self.textColor = SPNativeColors.gray
}
required init?(coder aDecoder: NSCoder) {
fatalError("init(coder:) has not been implemented")
super.init(coder: aDecoder)
self.commonInit()
}
internal func commonInit() {}
}
@@ -21,7 +21,7 @@
import UIKit
class SPFormButtonTableViewCell: UITableViewCell {
public class SPFormButtonTableViewCell: UITableViewCell {
let button = SPDownloadingButton()
@@ -51,14 +51,14 @@ class SPFormButtonTableViewCell: UITableViewCell {
self.contentView.addSubview(self.button)
}
override func prepareForReuse() {
override public func prepareForReuse() {
super.prepareForReuse()
self.button.setTitle("Button", for: .normal)
self.button.removeAllTargets()
self.selectionStyle = .none
}
override func layoutSubviews() {
override public func layoutSubviews() {
super.layoutSubviews()
self.button.setEqualsBoundsFromSuperview()
@@ -21,7 +21,7 @@
import UIKit
class SPFormFeaturedTitleTableViewCell: UITableViewCell {
public class SPFormFeaturedTitleTableViewCell: UITableViewCell {
let titleLabel = UILabel()
let button = SPDownloadingButton()
@@ -93,7 +93,7 @@ class SPFormFeaturedTitleTableViewCell: UITableViewCell {
self.button.centerYAnchor.constraint(equalTo: titleLabel.layoutMarginsGuide.centerYAnchor, constant: 0).isActive = true
}
override func prepareForReuse() {
override public func prepareForReuse() {
super.prepareForReuse()
self.titleLabel.text = "Title"
self.withButton = false
@@ -101,7 +101,7 @@ class SPFormFeaturedTitleTableViewCell: UITableViewCell {
self.type = .large
}
override func layoutSubviews() {
override public func layoutSubviews() {
super.layoutSubviews()
self.separatorInset.left = self.frame.width
@@ -21,7 +21,7 @@
import UIKit
class SPFormLabelTableViewCell: SPTableViewCell {
public class SPFormLabelTableViewCell: SPTableViewCell {
let label: UILabel = UILabel()
let descriptionLabel: UILabel = UILabel()
@@ -33,7 +33,7 @@ class SPFormLabelTableViewCell: SPTableViewCell {
return [self.descriptionLabel]
}
override var accessoryType: UITableViewCell.AccessoryType {
override public var accessoryType: UITableViewCell.AccessoryType {
didSet {
if self.accessoryType == .disclosureIndicator {
self.selectionStyle = .default
@@ -74,7 +74,7 @@ class SPFormLabelTableViewCell: SPTableViewCell {
self.accessoryType = .none
}
override func prepareForReuse() {
override public func prepareForReuse() {
super.prepareForReuse()
self.accessoryType = .none
self.label.text = "Title"
@@ -84,7 +84,7 @@ class SPFormLabelTableViewCell: SPTableViewCell {
self.fixWidthLabel = nil
}
override func layoutSubviews() {
override public func layoutSubviews() {
super.layoutSubviews()
let xPosition: CGFloat = (self.imageView?.frame.bottomXPosition ?? 0) + self.layoutMargins.left
@@ -21,6 +21,4 @@
import UIKit
class SPFormMailTableViewCell: SPBaseContentTableViewCell {
}
public class SPFormMailTableViewCell: SPBaseContentTableViewCell {}

Some files were not shown because too many files have changed in this diff Show More