-
Notifications
You must be signed in to change notification settings - Fork 184
/
Theme.swift
169 lines (135 loc) · 4.21 KB
/
Theme.swift
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
//
// Theme.swift
// RAMReel
//
// Created by Mikhail Stepkin on 4/11/15.
// Copyright (c) 2015 Ramotion. All rights reserved.
//
import UIKit
// MARK: Theme
/**
Theme
--
Protocol that allows you change visual appearance a bit.
*/
public protocol Theme {
/**
Text font of both list labels and input textfield.
*/
var font: UIFont { get }
/**
Color of textfield's text.
Suggestion list's text color is calculated using this color by changing alpha channel value to `0.3`.
*/
var textColor: UIColor { get }
/**
Color of list's background.
*/
var listBackgroundColor: UIColor { get }
}
/**
RAMTheme
--
Theme prefab.
*/
public struct RAMTheme: Theme {
/// Shared theme with default settings.
public static let sharedTheme = RAMTheme()
/// Theme font.
public let font: UIFont
/// Theme text color.
public let textColor: UIColor
/// Theme background color.
public let listBackgroundColor: UIColor
fileprivate init(
textColor: UIColor = UIColor.black,
listBackgroundColor: UIColor = UIColor.clear,
font: UIFont = RAMTheme.defaultFont
)
{
self.textColor = textColor
self.listBackgroundColor = listBackgroundColor
self.font = font
}
fileprivate static var defaultFont: UIFont = RAMTheme.initDefaultFont()
fileprivate static func initDefaultFont() -> UIFont {
do {
let _ = try FontLoader.loadRobotoLight()
} catch (let error) {
print(error)
}
let font: UIFont
if
let robotoLoaded = FontLoader.robotoLight,
let roboto = UIFont(name: robotoLoaded.name, size: 36)
{
font = roboto
} else if #available(iOS 8.2, *) {
font = UIFont.systemFont(ofSize: 36, weight: UIFont.Weight.thin)
} else {
font = UIFont.systemFont(ofSize: 36)
}
return font
}
/**
Creates new theme with new text color.
- parameter textColor: New text color.
- returns: New `RAMTheme` instance.
*/
public func textColor(_ textColor: UIColor) -> RAMTheme {
return RAMTheme(textColor: textColor, listBackgroundColor: self.listBackgroundColor, font: self.font)
}
/**
Creates new theme with new background color.
- parameter listBackgroundColor: New background color.
- returns: New `RAMTheme` instance.
*/
public func listBackgroundColor(_ listBackgroundColor: UIColor) -> RAMTheme {
return RAMTheme(textColor: self.textColor, listBackgroundColor: listBackgroundColor, font: self.font)
}
/**
Creates new theme with new font.
- parameter font: New font.
- returns: New `RAMTheme` instance.
*/
public func font(_ font: UIFont) -> RAMTheme {
return RAMTheme(textColor: self.textColor, listBackgroundColor: self.listBackgroundColor, font: font)
}
}
// MARK: - Font loader
/**
FontLoader
--
*/
final class FontLoader {
enum AnError: Error {
case failedToLoadFont(String)
}
static let robotoLight: FontLoader? = try? FontLoader.loadRobotoLight()
static func loadRobotoLight() throws -> FontLoader {
return try FontLoader(name: "Roboto-Light", type: "ttf")
}
let name: String
let type: String
fileprivate init(name: String, type: String) throws {
self.name = name
self.type = type
guard FontLoader.loadedFonts[name] == nil else {
return
}
let bundle = Bundle(for: Swift.type(of: self) as AnyClass)
if
let fontPath = bundle.path(forResource: name, ofType: type),
let inData = try? Data(contentsOf: URL(fileURLWithPath: fontPath)),
let provider = CGDataProvider(data: inData as CFData)
{
let font = CGFont(provider)
CTFontManagerRegisterGraphicsFont(font!, nil)
FontLoader.loadedFonts[self.name] = self
return
} else {
throw AnError.failedToLoadFont(name)
}
}
fileprivate static var loadedFonts: [String: FontLoader] = [:]
}