Skip to content

Commit 9725adc

Browse files
committed
Add preset .exclamation
1 parent 4c0a9bd commit 9725adc

File tree

8 files changed

+161
-2
lines changed

8 files changed

+161
-2
lines changed
Lines changed: 10 additions & 0 deletions
Loading

Assets/Sketch/Presets.sketch

7.61 KB
Binary file not shown.

Example/Controllers/ViewController.swift

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,7 @@ class ViewController: UITableViewController {
1010
Alert(key: "Bookmark", preset: .bookmark, title: "Added to bookmark", subtitle: "See bookmarks screen"),
1111
Alert(key: "Moon", preset: .moon, title: "Night Mode", subtitle: "You can disable it in settings"),
1212
Alert(key: "Star", preset: .star, title: "Added to favorite", subtitle: nil),
13+
Alert(key: "Exclamation", preset: .exclamation, title: "Oops", subtitle: "Something went wrong"),
1314
Alert(key: "Add", preset: .add, title: "Added to Folder", subtitle: nil),
1415
Alert(key: "Error", preset: .error, title: "Oops", subtitle: "Please try again later"),
1516
Alert(key: "Message", preset: nil, title: nil, subtitle: "Email required")
@@ -46,6 +47,9 @@ class ViewController: UITableViewController {
4647
tableView.register(UITableViewCell.self, forCellReuseIdentifier: "cell")
4748
}
4849

50+
/**
51+
Show now. Call when tap on nav-bar item.
52+
*/
4953
@objc func showAlert() {
5054
let alertData = data[selectedIndexPath.row]
5155
if let preset = alertData.preset {
@@ -55,6 +59,14 @@ class ViewController: UITableViewController {
5559
}
5660
}
5761

62+
/**
63+
Alert preview data.
64+
65+
- parameter key: Visible ID in table view.
66+
- parameter preset: Preset for `SPAlert`.
67+
- parameter title: Title in `SPAlert`. Optional only for `.message` preset.
68+
- parameter subtitle: Optional subtitle in `SPAlert`.
69+
*/
5870
typealias Alert = (key: String, preset: SPAlertPreset?, title: String?, subtitle: String?)
5971
}
6072

Readme.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,7 @@ And other
1515
<img src="https://github.com/ivanvorobei/SPAlert/blob/master/Assets/Readme/Miniature%20-%20Bookmark.svg" width="55">
1616
<img src="https://github.com/ivanvorobei/SPAlert/blob/master/Assets/Readme/Miniature%20-%20Moon.svg" width="55">
1717
<img src="https://github.com/ivanvorobei/SPAlert/blob/master/Assets/Readme/Miniature%20-%20Star.svg" width="55">
18+
<img src="https://github.com/ivanvorobei/SPAlert/blob/master/Assets/Readme/Miniature%20-%20Exclamation.svg" width="55">
1819
<img src="https://github.com/ivanvorobei/SPAlert/blob/master/Assets/Readme/Miniature%20-%20Add.svg" width="55">
1920
<img src="https://github.com/ivanvorobei/SPAlert/blob/master/Assets/Readme/Miniature%20-%20Error.svg" width="55">
2021
</p>

SPAlert.podspec

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,8 @@
11
Pod::Spec.new do |s|
22

33
s.name = "SPAlert"
4-
s.version = "2.0.6"
5-
s.summary = "Native alert from Apple Music & Feedback. Contains Done, Heart & Message presets."
4+
s.version = "2.0.8"
5+
s.summary = "Native alert from Apple Music & Feedback. Contains Done, Heart & Message and other presets."
66
s.homepage = "https://github.com/IvanVorobei/SPAlert"
77
s.source = { :git => "https://github.com/IvanVorobei/SPAlert.git", :tag => s.version }
88
s.license = { :type => "MIT", :file => "LICENSE" }

SPAlert.xcodeproj/project.pbxproj

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -28,6 +28,7 @@
2828
F4CA67B5238ABD0100E72F79 /* SPAlertIconAddView.swift in Sources */ = {isa = PBXBuildFile; fileRef = F4CA67B4238ABD0100E72F79 /* SPAlertIconAddView.swift */; };
2929
F4D3CD58238DA9FE006C3DE2 /* SPAlertIconMoonView.swift in Sources */ = {isa = PBXBuildFile; fileRef = F4D3CD57238DA9FE006C3DE2 /* SPAlertIconMoonView.swift */; };
3030
F4D3CD5A238DAA49006C3DE2 /* SPAlertIconStarView.swift in Sources */ = {isa = PBXBuildFile; fileRef = F4D3CD59238DAA49006C3DE2 /* SPAlertIconStarView.swift */; };
31+
F4E4459D2390524A0067FF5C /* SPAlertIconExclamationView.swift in Sources */ = {isa = PBXBuildFile; fileRef = F4E4459C2390524A0067FF5C /* SPAlertIconExclamationView.swift */; };
3132
/* End PBXBuildFile section */
3233

3334
/* Begin PBXContainerItemProxy section */
@@ -84,6 +85,7 @@
8485
F4CA67B4238ABD0100E72F79 /* SPAlertIconAddView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = SPAlertIconAddView.swift; sourceTree = "<group>"; };
8586
F4D3CD57238DA9FE006C3DE2 /* SPAlertIconMoonView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = SPAlertIconMoonView.swift; sourceTree = "<group>"; };
8687
F4D3CD59238DAA49006C3DE2 /* SPAlertIconStarView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = SPAlertIconStarView.swift; sourceTree = "<group>"; };
88+
F4E4459C2390524A0067FF5C /* SPAlertIconExclamationView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = SPAlertIconExclamationView.swift; sourceTree = "<group>"; };
8789
/* End PBXFileReference section */
8890

8991
/* Begin PBXFrameworksBuildPhase section */
@@ -169,6 +171,7 @@
169171
F4CA67B4238ABD0100E72F79 /* SPAlertIconAddView.swift */,
170172
F4D3CD57238DA9FE006C3DE2 /* SPAlertIconMoonView.swift */,
171173
F4D3CD59238DAA49006C3DE2 /* SPAlertIconStarView.swift */,
174+
F4E4459C2390524A0067FF5C /* SPAlertIconExclamationView.swift */,
172175
);
173176
path = Icons;
174177
sourceTree = "<group>";
@@ -366,6 +369,7 @@
366369
files = (
367370
F412052A2382AF64009C2AC7 /* SPAlertHaptic.swift in Sources */,
368371
F41204EE2382AC9B009C2AC7 /* SPAlert.swift in Sources */,
372+
F4E4459D2390524A0067FF5C /* SPAlertIconExclamationView.swift in Sources */,
369373
F41204EA2382AC9B009C2AC7 /* SPAlertPreset.swift in Sources */,
370374
F4A5A92C2388792F00B0DFE0 /* SPAlertIconBookmarkView.swift in Sources */,
371375
F41204EC2382AC9B009C2AC7 /* SPAlertIconDoneView.swift in Sources */,

Source/SPAlert/Models/SPAlertPreset.swift

Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -32,6 +32,7 @@ public enum SPAlertPreset {
3232
case bookmark
3333
case moon
3434
case star
35+
case exclamation
3536
case add
3637
case error
3738

@@ -52,6 +53,8 @@ public enum SPAlertPreset {
5253
return SPAlertIconAddView()
5354
case .moon:
5455
return SPAlertIconMoonView()
56+
case .exclamation:
57+
return SPAlertIconExclamationView()
5558
case .star:
5659
return SPAlertIconStarView()
5760
case .error:
@@ -80,6 +83,14 @@ public enum SPAlertPreset {
8083
layout.iconHeight = 77
8184
layout.bottomIconSpace = 35
8285
return layout
86+
case .exclamation:
87+
var layout = SPAlertLayout()
88+
layout.topSpace = 46
89+
layout.bottomSpace = 33
90+
layout.iconWidth = 112
91+
layout.iconHeight = 90
92+
layout.bottomIconSpace = 31
93+
return layout
8394
case .doc:
8495
var layout = SPAlertLayout()
8596
layout.topSpace = 49
@@ -150,6 +161,8 @@ public enum SPAlertPreset {
150161
return .success
151162
case .moon:
152163
return .success
164+
case .exclamation:
165+
return .warning
153166
case .error:
154167
return .error
155168
}
Lines changed: 119 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,119 @@
1+
// The MIT License (MIT)
2+
// Copyright © 2019 Ivan Vorobei ([email protected])
3+
//
4+
// Permission is hereby granted, free of charge, to any person obtaining a copy
5+
// of this software and associated documentation files (the "Software"), to deal
6+
// in the Software without restriction, including without limitation the rights
7+
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
8+
// copies of the Software, and to permit persons to whom the Software is
9+
// furnished to do so, subject to the following conditions:
10+
//
11+
// The above copyright notice and this permission notice shall be included in all
12+
// copies or substantial portions of the Software.
13+
//
14+
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
15+
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
16+
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
17+
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
18+
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
19+
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
20+
// SOFTWARE.
21+
22+
import UIKit
23+
24+
public class SPAlertIconExclamationView: UIView {
25+
26+
init() {
27+
super.init(frame: .zero)
28+
self.backgroundColor = .clear
29+
}
30+
31+
required init?(coder aDecoder: NSCoder) {
32+
fatalError("init(coder:) has not been implemented")
33+
}
34+
35+
public override func draw(_ rect: CGRect) {
36+
super.draw(rect)
37+
ExclamationDraw.draw(frame: rect, resizing: .aspectFit, fillColor: self.tintColor)
38+
}
39+
40+
class ExclamationDraw: NSObject {
41+
42+
@objc dynamic public class func draw(frame targetFrame: CGRect = CGRect(x: 0, y: 0, width: 65, height: 65), resizing: ResizingBehavior = .aspectFit, fillColor: UIColor = UIColor(red: 0.349, green: 0.345, blue: 0.353, alpha: 1.000)) {
43+
let context = UIGraphicsGetCurrentContext()!
44+
context.saveGState()
45+
let resizedFrame: CGRect = resizing.apply(rect: CGRect(x: 0, y: 0, width: 58, height: 52), target: targetFrame)
46+
context.translateBy(x: resizedFrame.minX, y: resizedFrame.minY)
47+
context.scaleBy(x: resizedFrame.width / 58, y: resizedFrame.height / 52)
48+
let bezierPath = UIBezierPath()
49+
bezierPath.move(to: CGPoint(x: 9.05, y: 50))
50+
bezierPath.addLine(to: CGPoint(x: 48.02, y: 50))
51+
bezierPath.addCurve(to: CGPoint(x: 54.07, y: 43.95), controlPoint1: CGPoint(x: 51.74, y: 50), controlPoint2: CGPoint(x: 54.07, y: 47.32))
52+
bezierPath.addCurve(to: CGPoint(x: 53.27, y: 40.97), controlPoint1: CGPoint(x: 54.07, y: 42.93), controlPoint2: CGPoint(x: 53.82, y: 41.91))
53+
bezierPath.addLine(to: CGPoint(x: 33.75, y: 6.05))
54+
bezierPath.addCurve(to: CGPoint(x: 28.55, y: 3), controlPoint1: CGPoint(x: 32.64, y: 4.04), controlPoint2: CGPoint(x: 30.58, y: 3))
55+
bezierPath.addCurve(to: CGPoint(x: 23.31, y: 6.05), controlPoint1: CGPoint(x: 26.49, y: 3), controlPoint2: CGPoint(x: 24.43, y: 4.04))
56+
bezierPath.addLine(to: CGPoint(x: 3.82, y: 41))
57+
bezierPath.addCurve(to: CGPoint(x: 3, y: 43.95), controlPoint1: CGPoint(x: 3.27, y: 41.94), controlPoint2: CGPoint(x: 3, y: 42.93))
58+
bezierPath.addCurve(to: CGPoint(x: 9.05, y: 50), controlPoint1: CGPoint(x: 3, y: 47.32), controlPoint2: CGPoint(x: 5.33, y: 50))
59+
bezierPath.close()
60+
bezierPath.move(to: CGPoint(x: 28.55, y: 33.01))
61+
bezierPath.addCurve(to: CGPoint(x: 26.46, y: 30.93), controlPoint1: CGPoint(x: 27.23, y: 33.01), controlPoint2: CGPoint(x: 26.51, y: 32.27))
62+
bezierPath.addLine(to: CGPoint(x: 26.12, y: 18.67))
63+
bezierPath.addCurve(to: CGPoint(x: 28.52, y: 16.34), controlPoint1: CGPoint(x: 26.07, y: 17.34), controlPoint2: CGPoint(x: 27.11, y: 16.34))
64+
bezierPath.addCurve(to: CGPoint(x: 30.93, y: 18.7), controlPoint1: CGPoint(x: 29.91, y: 16.34), controlPoint2: CGPoint(x: 30.98, y: 17.36))
65+
bezierPath.addLine(to: CGPoint(x: 30.58, y: 30.93))
66+
bezierPath.addCurve(to: CGPoint(x: 28.55, y: 33.01), controlPoint1: CGPoint(x: 30.53, y: 32.29), controlPoint2: CGPoint(x: 29.79, y: 33.01))
67+
bezierPath.close()
68+
bezierPath.move(to: CGPoint(x: 28.55, y: 42.16))
69+
bezierPath.addCurve(to: CGPoint(x: 25.77, y: 39.48), controlPoint1: CGPoint(x: 27.11, y: 42.16), controlPoint2: CGPoint(x: 25.77, y: 41.02))
70+
bezierPath.addCurve(to: CGPoint(x: 28.55, y: 36.81), controlPoint1: CGPoint(x: 25.77, y: 37.95), controlPoint2: CGPoint(x: 27.08, y: 36.81))
71+
bezierPath.addCurve(to: CGPoint(x: 31.32, y: 39.48), controlPoint1: CGPoint(x: 29.98, y: 36.81), controlPoint2: CGPoint(x: 31.32, y: 37.92))
72+
bezierPath.addCurve(to: CGPoint(x: 28.55, y: 42.16), controlPoint1: CGPoint(x: 31.32, y: 41.05), controlPoint2: CGPoint(x: 29.96, y: 42.16))
73+
bezierPath.close()
74+
fillColor.setFill()
75+
bezierPath.fill()
76+
context.restoreGState()
77+
}
78+
79+
@objc(StyleKitNameResizingBehavior)
80+
public enum ResizingBehavior: Int {
81+
82+
case aspectFit
83+
case aspectFill
84+
case stretch
85+
case center
86+
87+
public func apply(rect: CGRect, target: CGRect) -> CGRect {
88+
if rect == target || target == CGRect.zero {
89+
return rect
90+
}
91+
92+
var scales = CGSize.zero
93+
scales.width = abs(target.width / rect.width)
94+
scales.height = abs(target.height / rect.height)
95+
96+
switch self {
97+
case .aspectFit:
98+
scales.width = min(scales.width, scales.height)
99+
scales.height = scales.width
100+
case .aspectFill:
101+
scales.width = max(scales.width, scales.height)
102+
scales.height = scales.width
103+
case .stretch:
104+
break
105+
case .center:
106+
scales.width = 1
107+
scales.height = 1
108+
}
109+
110+
var result = rect.standardized
111+
result.size.width *= scales.width
112+
result.size.height *= scales.height
113+
result.origin.x = target.minX + (target.width - result.width) / 2
114+
result.origin.y = target.minY + (target.height - result.height) / 2
115+
return result
116+
}
117+
}
118+
}
119+
}

0 commit comments

Comments
 (0)