mirror of https://github.com/xaoxuu/ProHUD
update
This commit is contained in:
parent
0da83c80b5
commit
34e7b0ffbb
|
@ -8,6 +8,7 @@
|
|||
|
||||
import UIKit
|
||||
import SnapKit
|
||||
import Inspire
|
||||
|
||||
public extension ProHUD.Configuration {
|
||||
struct Alert {
|
||||
|
@ -60,7 +61,7 @@ public extension ProHUD.Configuration {
|
|||
}
|
||||
|
||||
/// 多少秒后显示强制退出的按钮(只有无按钮的弹窗才会出现)
|
||||
public var forceQuitTimer = TimeInterval(10)
|
||||
public var forceQuitTimer = TimeInterval(30)
|
||||
|
||||
/// 强制退出按钮标题
|
||||
public var forceQuitTitle = "隐藏窗口"
|
||||
|
@ -104,9 +105,10 @@ fileprivate var privLoadSubviews: (ProHUD.Alert) -> Void = {
|
|||
vc.contentView.layer.masksToBounds = true
|
||||
vc.contentView.layer.cornerRadius = cfg.alert.cornerRadius
|
||||
|
||||
let maxWidth = CGFloat.maximum(CGFloat.minimum(UIScreen.main.bounds.width * 0.68, cfg.alert.maxWidth), 268)
|
||||
vc.contentView.snp.makeConstraints { (mk) in
|
||||
mk.center.equalToSuperview()
|
||||
mk.width.lessThanOrEqualTo(CGFloat.minimum(UIScreen.main.bounds.width * 0.68, cfg.alert.maxWidth))
|
||||
mk.width.lessThanOrEqualTo(maxWidth)
|
||||
}
|
||||
vc.contentStack.snp.makeConstraints { (mk) in
|
||||
mk.centerX.equalToSuperview()
|
||||
|
@ -180,8 +182,13 @@ fileprivate var privReloadData: (ProHUD.Alert) -> Void = {
|
|||
vc.textStack.snp.makeConstraints { (mk) in
|
||||
mk.top.greaterThanOrEqualTo(vc.contentView).offset(config.padding*1.75)
|
||||
mk.bottom.lessThanOrEqualTo(vc.contentView).offset(-config.padding*1.75)
|
||||
mk.leading.greaterThanOrEqualTo(vc.contentView).offset(config.padding*2)
|
||||
mk.trailing.lessThanOrEqualTo(vc.contentView).offset(-config.padding*2)
|
||||
if UIScreen.main.bounds.width < 414 {
|
||||
mk.leading.greaterThanOrEqualTo(vc.contentView).offset(config.padding*1.5)
|
||||
mk.trailing.lessThanOrEqualTo(vc.contentView).offset(-config.padding*1.5)
|
||||
} else {
|
||||
mk.leading.greaterThanOrEqualTo(vc.contentView).offset(config.padding*2)
|
||||
mk.trailing.lessThanOrEqualTo(vc.contentView).offset(-config.padding*2)
|
||||
}
|
||||
}
|
||||
if vc.model.title?.count ?? 0 > 0 {
|
||||
if let lb = vc.titleLabel {
|
||||
|
@ -273,12 +280,12 @@ fileprivate var privReloadData: (ProHUD.Alert) -> Void = {
|
|||
}
|
||||
switch vc.model.scene {
|
||||
case .loading:
|
||||
vc.model.duration = nil
|
||||
vc.duration(nil)
|
||||
default:
|
||||
vc.model.duration = 2
|
||||
vc.duration(2)
|
||||
}
|
||||
if vc.actionStack.arrangedSubviews.count > 0 {
|
||||
vc.model.duration = nil
|
||||
vc.duration(nil)
|
||||
}
|
||||
}
|
||||
}()
|
||||
|
|
|
@ -115,8 +115,8 @@ public extension ProHUD.Alert {
|
|||
/// - Parameter style: 样式
|
||||
/// - Parameter text: 标题
|
||||
/// - Parameter action: 事件
|
||||
@discardableResult func add(action style: UIAlertAction.Style, title: String?, action: (() -> Void)?) -> ProHUD.Alert {
|
||||
if let btn = privAddButton(custom: Button.actionButton(title: title), action: action) as? Button {
|
||||
@discardableResult func add(action style: UIAlertAction.Style, title: String?, handler: (() -> Void)?) -> ProHUD.Alert {
|
||||
if let btn = privAddButton(custom: Button.actionButton(title: title), action: handler) as? Button {
|
||||
btn.update(style: style)
|
||||
}
|
||||
return self
|
||||
|
@ -147,8 +147,9 @@ public extension ProHUD.Alert {
|
|||
/// 设置持续时间
|
||||
/// - Parameter duration: 持续时间
|
||||
@discardableResult func duration(_ duration: TimeInterval?) -> ProHUD.Alert {
|
||||
model.duration = duration
|
||||
willLayoutSubviews()
|
||||
model.setupDuration(duration: duration) { [weak self] in
|
||||
self?.pop()
|
||||
}
|
||||
return self
|
||||
}
|
||||
|
||||
|
@ -240,6 +241,7 @@ public extension ProHUD {
|
|||
alerts.append(alert)
|
||||
}
|
||||
updateAlertsLayout()
|
||||
|
||||
// setup duration
|
||||
if let _ = alert.model.duration, alert.model.durationBlock == nil {
|
||||
alert.duration(alert.model.duration)
|
||||
|
@ -252,8 +254,11 @@ public extension ProHUD {
|
|||
/// - Parameter title: 标题
|
||||
/// - Parameter message: 正文
|
||||
/// - Parameter icon: 图标
|
||||
@discardableResult func push(alert scene: Alert.Scene, title: String? = nil, message: String? = nil) -> Alert {
|
||||
return push(Alert(scene: scene, title: title, message: message))
|
||||
@discardableResult func push(alert scene: Alert.Scene, title: String? = nil, message: String? = nil, actions: ((Alert) -> Void)? = nil) -> Alert {
|
||||
let a = Alert(scene: scene, title: title, message: message)
|
||||
actions?(a)
|
||||
a.view.layoutIfNeeded()
|
||||
return push(a)
|
||||
}
|
||||
|
||||
/// 获取指定的实例
|
||||
|
@ -306,8 +311,8 @@ public extension ProHUD {
|
|||
/// - Parameter title: 标题
|
||||
/// - Parameter message: 正文
|
||||
/// - Parameter icon: 图标
|
||||
@discardableResult class func push(alert: Alert.Scene, title: String? = nil, message: String? = nil) -> Alert {
|
||||
return shared.push(alert: alert, title: title, message: message)
|
||||
@discardableResult class func push(alert: Alert.Scene, title: String? = nil, message: String? = nil, actions: ((Alert) -> Void)? = nil) -> Alert {
|
||||
return shared.push(alert: alert, title: title, message: message, actions: actions)
|
||||
}
|
||||
|
||||
/// 获取指定的实例
|
||||
|
@ -362,10 +367,6 @@ fileprivate extension ProHUD.Alert {
|
|||
// 布局
|
||||
cfg.alert.loadSubviews(a)
|
||||
cfg.alert.reloadData(a)
|
||||
// 持续时间
|
||||
a.model.setupDuration(duration: a.model.duration) { [weak self] in
|
||||
self?.pop()
|
||||
}
|
||||
// 强制退出按钮
|
||||
a.model.setupForceQuit(duration: cfg.alert.forceQuitTimer) { [weak self] in
|
||||
if let aa = self, aa.actionStack.superview == nil {
|
||||
|
|
|
@ -29,7 +29,8 @@ public extension ProHUD.Configuration {
|
|||
// MARK: 文本样式
|
||||
/// 标题字体
|
||||
public var titleFont = UIFont.boldSystemFont(ofSize: 22)
|
||||
|
||||
/// 副标题字体
|
||||
public var subTitleFont = UIFont.boldSystemFont(ofSize: 20)
|
||||
/// 正文字体
|
||||
public var bodyFont = UIFont.systemFont(ofSize: 18)
|
||||
|
||||
|
@ -64,6 +65,21 @@ internal extension ProHUD.Configuration.Guard {
|
|||
var reloadData: (ProHUD.Guard) -> Void {
|
||||
return privReloadData
|
||||
}
|
||||
var reloadStack: (ProHUD.Guard) -> Void {
|
||||
return { (vc) in
|
||||
if vc.textStack.arrangedSubviews.count > 0 {
|
||||
vc.contentStack.addArrangedSubview(vc.textStack)
|
||||
} else {
|
||||
vc.textStack.removeFromSuperview()
|
||||
}
|
||||
if vc.actionStack.arrangedSubviews.count > 0 {
|
||||
vc.contentStack.addArrangedSubview(vc.actionStack)
|
||||
} else {
|
||||
vc.actionStack.removeFromSuperview()
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
fileprivate var privLoadSubviews: (ProHUD.Guard) -> Void = {
|
||||
|
@ -75,8 +91,6 @@ fileprivate var privLoadSubviews: (ProHUD.Guard) -> Void = {
|
|||
vc.view.backgroundColor = UIColor(white: 0, alpha: 0)
|
||||
vc.view.addSubview(vc.contentView)
|
||||
vc.contentView.contentView.addSubview(vc.contentStack)
|
||||
vc.contentStack.addArrangedSubview(vc.textStack)
|
||||
vc.contentStack.addArrangedSubview(vc.actionStack)
|
||||
}
|
||||
}()
|
||||
|
||||
|
@ -116,7 +130,7 @@ fileprivate var privReloadData: (ProHUD.Guard) -> Void = {
|
|||
if width == config.cardMaxWidth {
|
||||
mk.bottom.equalToSuperview().offset(-config.padding)
|
||||
} else {
|
||||
mk.bottom.equalToSuperview().offset(-config.margin-Inspire.shared.screen.safeAreaInsets.bottom)
|
||||
mk.bottom.equalToSuperview().offset(-config.padding-Inspire.shared.screen.safeAreaInsets.bottom)
|
||||
}
|
||||
if isPortrait {
|
||||
mk.width.equalToSuperview().offset(-config.padding * 2)
|
||||
|
@ -124,5 +138,6 @@ fileprivate var privReloadData: (ProHUD.Guard) -> Void = {
|
|||
mk.width.equalToSuperview().offset(-config.padding * 4)
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
}()
|
||||
|
|
|
@ -45,6 +45,9 @@ public extension ProHUD {
|
|||
/// 是否正在显示
|
||||
private var displaying = false
|
||||
|
||||
/// 背景颜色
|
||||
public var backgroundColor: UIColor? = UIColor(white: 0, alpha: 0.5)
|
||||
|
||||
// MARK: 生命周期
|
||||
|
||||
/// 实例化
|
||||
|
@ -64,6 +67,7 @@ public extension ProHUD {
|
|||
}
|
||||
cfg.guard.loadSubviews(self)
|
||||
cfg.guard.reloadData(self)
|
||||
cfg.guard.reloadStack(self)
|
||||
|
||||
// 点击
|
||||
let tap = UITapGestureRecognizer(target: self, action: #selector(privDidTapped(_:)))
|
||||
|
@ -85,7 +89,8 @@ public extension ProHUD.Guard {
|
|||
/// 推入某个视图控制器
|
||||
/// - Parameter viewController: 视图控制器
|
||||
func push(to viewController: UIViewController? = nil) {
|
||||
if let vc = viewController {
|
||||
func f(_ vc: UIViewController) {
|
||||
ProHUD.pop(guard: vc, animated: false)
|
||||
view.layoutIfNeeded()
|
||||
vc.addChild(self)
|
||||
vc.view.addSubview(view)
|
||||
|
@ -101,20 +106,30 @@ public extension ProHUD.Guard {
|
|||
self.translateIn()
|
||||
}
|
||||
}
|
||||
// FIXME: 如果传入vc为空,则push到根控制器
|
||||
|
||||
if let vc = viewController ?? cfg.rootViewController {
|
||||
f(vc)
|
||||
} else {
|
||||
debug("请传入需要push到的控制器")
|
||||
}
|
||||
}
|
||||
|
||||
/// 从父视图控制器弹出
|
||||
func pop() {
|
||||
func pop(animated: Bool = true) {
|
||||
if displaying {
|
||||
debug("pop")
|
||||
displaying = false
|
||||
view.isUserInteractionEnabled = false
|
||||
self.removeFromParent()
|
||||
UIView.animateForGuard(animations: {
|
||||
if animated {
|
||||
UIView.animateForGuard(animations: {
|
||||
self.translateOut()
|
||||
}) { (done) in
|
||||
if self.displaying == false {
|
||||
self.view.removeFromSuperview()
|
||||
}
|
||||
}
|
||||
} else {
|
||||
self.translateOut()
|
||||
}) { (done) in
|
||||
if self.displaying == false {
|
||||
self.view.removeFromSuperview()
|
||||
}
|
||||
|
@ -140,6 +155,15 @@ public extension ProHUD.Guard {
|
|||
} else {
|
||||
// Fallback on earlier versions
|
||||
}
|
||||
cfg.guard.reloadStack(self)
|
||||
return lb
|
||||
}
|
||||
|
||||
/// 加载一个副标题
|
||||
/// - Parameter text: 文本
|
||||
@discardableResult func add(subTitle: String?) -> UILabel {
|
||||
let lb = add(title: subTitle)
|
||||
lb.font = cfg.guard.subTitleFont
|
||||
return lb
|
||||
}
|
||||
|
||||
|
@ -153,6 +177,7 @@ public extension ProHUD.Guard {
|
|||
lb.textAlignment = .justified
|
||||
lb.text = message
|
||||
textStack.addArrangedSubview(lb)
|
||||
cfg.guard.reloadStack(self)
|
||||
return lb
|
||||
}
|
||||
|
||||
|
@ -163,10 +188,8 @@ public extension ProHUD.Guard {
|
|||
@discardableResult func add(action style: UIAlertAction.Style, title: String?, action: (() -> Void)?) -> UIButton {
|
||||
let btn = Button.actionButton(title: title)
|
||||
btn.titleLabel?.font = cfg.guard.buttonFont
|
||||
if actionStack.superview == nil {
|
||||
contentStack.addArrangedSubview(actionStack)
|
||||
}
|
||||
actionStack.addArrangedSubview(btn)
|
||||
cfg.guard.reloadStack(self)
|
||||
btn.update(style: style)
|
||||
addTouchUpAction(for: btn) { [weak self] in
|
||||
action?()
|
||||
|
@ -177,6 +200,14 @@ public extension ProHUD.Guard {
|
|||
return btn
|
||||
}
|
||||
|
||||
/// 移除按钮
|
||||
/// - Parameter index: 索引
|
||||
@discardableResult func remove(action index: Int...) -> ProHUD.Guard {
|
||||
for (i, idx) in index.enumerated() {
|
||||
privRemoveAction(index: idx-i)
|
||||
}
|
||||
return self
|
||||
}
|
||||
|
||||
/// 消失事件
|
||||
/// - Parameter callback: 事件回调
|
||||
|
@ -203,8 +234,10 @@ public extension ProHUD {
|
|||
/// - Parameter title: 标题
|
||||
/// - Parameter message: 正文
|
||||
/// - Parameter icon: 图标
|
||||
@discardableResult func push(guard viewController: UIViewController? = nil, title: String? = nil, message: String? = nil) -> Guard {
|
||||
@discardableResult func push(guard viewController: UIViewController? = nil, title: String? = nil, message: String? = nil, actions: ((Guard) -> Void)? = nil) -> Guard {
|
||||
let g = Guard(title: title, message: message)
|
||||
actions?(g)
|
||||
g.view.layoutIfNeeded()
|
||||
g.push(to: viewController)
|
||||
return g
|
||||
}
|
||||
|
@ -215,6 +248,20 @@ public extension ProHUD {
|
|||
`guard`.pop()
|
||||
}
|
||||
|
||||
/// 弹出屏幕
|
||||
/// - Parameter alert: 从哪里
|
||||
func pop(guard from: UIViewController?, animated: Bool = true) {
|
||||
if let vc = from {
|
||||
for c in vc.children {
|
||||
if c.isKind(of: Guard.self) {
|
||||
if let cc = c as? Guard {
|
||||
cc.pop(animated: animated)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
// MARK: 类函数
|
||||
|
@ -232,8 +279,8 @@ public extension ProHUD {
|
|||
/// - Parameter title: 标题
|
||||
/// - Parameter message: 正文
|
||||
/// - Parameter icon: 图标
|
||||
@discardableResult class func push(guard viewController: UIViewController? = nil, title: String? = nil, message: String? = nil) -> Guard {
|
||||
return shared.push(guard: viewController, title: title, message: message)
|
||||
@discardableResult class func push(guard viewController: UIViewController? = nil, title: String? = nil, message: String? = nil, actions: ((Guard) -> Void)? = nil) -> Guard {
|
||||
return shared.push(guard: viewController, title: title, message: message, actions: actions)
|
||||
}
|
||||
|
||||
/// 弹出屏幕
|
||||
|
@ -242,6 +289,12 @@ public extension ProHUD {
|
|||
shared.pop(`guard`)
|
||||
}
|
||||
|
||||
/// 弹出屏幕
|
||||
/// - Parameter alert: 从哪里
|
||||
class func pop(guard from: UIViewController?, animated: Bool = true) {
|
||||
shared.pop(guard: from, animated: animated)
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
|
@ -265,7 +318,7 @@ fileprivate extension ProHUD.Guard {
|
|||
}
|
||||
|
||||
func translateIn() {
|
||||
view.backgroundColor = UIColor(white: 0, alpha: 0.5)
|
||||
view.backgroundColor = backgroundColor
|
||||
contentView.transform = .identity
|
||||
}
|
||||
|
||||
|
@ -274,6 +327,25 @@ fileprivate extension ProHUD.Guard {
|
|||
contentView.transform = .init(translationX: 0, y: view.frame.size.height - contentView.frame.minY + cfg.guard.margin)
|
||||
}
|
||||
|
||||
/// 移除按钮
|
||||
/// - Parameter index: 索引
|
||||
@discardableResult func privRemoveAction(index: Int) -> ProHUD.Guard {
|
||||
if index < 0 {
|
||||
for view in self.actionStack.arrangedSubviews {
|
||||
if let btn = view as? UIButton {
|
||||
btn.removeFromSuperview()
|
||||
}
|
||||
}
|
||||
} else if index < self.actionStack.arrangedSubviews.count, let btn = self.actionStack.arrangedSubviews[index] as? UIButton {
|
||||
btn.removeFromSuperview()
|
||||
}
|
||||
cfg.guard.reloadStack(self)
|
||||
UIView.animateForAlert {
|
||||
self.view.layoutIfNeeded()
|
||||
}
|
||||
return self
|
||||
}
|
||||
|
||||
|
||||
|
||||
}
|
||||
|
|
|
@ -14,26 +14,29 @@ public extension ProHUD {
|
|||
/// 是否允许Debug模式输出
|
||||
public var enableDebugPrint = true
|
||||
|
||||
/// 根控制器
|
||||
public var rootViewController: UIViewController?
|
||||
|
||||
/// 动态颜色(适配iOS13)
|
||||
public lazy var dynamicColor: UIColor = {
|
||||
if #available(iOS 13.0, *) {
|
||||
let color = UIColor { (traitCollection: UITraitCollection) -> UIColor in
|
||||
if traitCollection.userInterfaceStyle == .dark {
|
||||
return .white
|
||||
} else {
|
||||
return .black
|
||||
}
|
||||
}
|
||||
return color
|
||||
} else {
|
||||
// Fallback on earlier versions
|
||||
}
|
||||
return .init(white: 0.2, alpha: 1)
|
||||
// if #available(iOS 13.0, *) {
|
||||
// let color = UIColor { (traitCollection: UITraitCollection) -> UIColor in
|
||||
// if traitCollection.userInterfaceStyle == .dark {
|
||||
// return .white
|
||||
// } else {
|
||||
// return .black
|
||||
// }
|
||||
// }
|
||||
// return color
|
||||
// } else {
|
||||
// // Fallback on earlier versions
|
||||
// }
|
||||
return .init(white: 0.15, alpha: 1)
|
||||
}()
|
||||
|
||||
/// 主标签文本颜色
|
||||
public lazy var primaryLabelColor: UIColor = {
|
||||
return dynamicColor.withAlphaComponent(0.75)
|
||||
return dynamicColor.withAlphaComponent(0.8)
|
||||
}()
|
||||
|
||||
/// 次级标签文本颜色
|
||||
|
|
|
@ -29,7 +29,7 @@ public class HUDController: UIViewController {
|
|||
}
|
||||
|
||||
deinit {
|
||||
debug(self, "deinit")
|
||||
debug("👌", self, "deinit")
|
||||
}
|
||||
|
||||
|
||||
|
|
|
@ -32,7 +32,8 @@ public extension ProHUD {
|
|||
init() {
|
||||
|
||||
if #available(iOS 13.0, *) {
|
||||
super.init(effect: UIBlurEffect(style: .systemMaterial))
|
||||
// super.init(effect: UIBlurEffect(style: .systemMaterial))
|
||||
super.init(effect: UIBlurEffect(style: .extraLight))
|
||||
} else if #available(iOS 11.0, *) {
|
||||
super.init(effect: UIBlurEffect(style: .extraLight))
|
||||
} else {
|
||||
|
|
|
@ -125,9 +125,9 @@ fileprivate var privReloadData: (ProHUD.Toast) -> Void = {
|
|||
vc.view.layoutIfNeeded()
|
||||
switch vc.model.scene {
|
||||
case .loading:
|
||||
vc.model.duration = nil
|
||||
vc.duration(nil)
|
||||
default:
|
||||
vc.model.duration = 3
|
||||
vc.duration(3)
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
@ -45,9 +45,13 @@ public extension ProHUD {
|
|||
public var backgroundView: UIVisualEffectView = {
|
||||
let vev = UIVisualEffectView()
|
||||
if #available(iOS 13.0, *) {
|
||||
vev.effect = UIBlurEffect.init(style: .systemMaterial)
|
||||
} else {
|
||||
// vev.effect = UIBlurEffect.init(style: .systemMaterial))
|
||||
vev.effect = UIBlurEffect.init(style: .extraLight)
|
||||
} else if #available(iOS 11.0, *) {
|
||||
vev.effect = UIBlurEffect.init(style: .extraLight)
|
||||
} else {
|
||||
vev.effect = .none
|
||||
vev.backgroundColor = .white
|
||||
}
|
||||
vev.layer.masksToBounds = true
|
||||
vev.layer.cornerRadius = cfg.toast.cornerRadius
|
||||
|
@ -272,8 +276,11 @@ public extension ProHUD {
|
|||
/// - Parameter title: 标题
|
||||
/// - Parameter message: 内容
|
||||
/// - Parameter icon: 图标
|
||||
@discardableResult func push(toast scene: Toast.Scene, title: String? = nil, message: String? = nil) -> Toast {
|
||||
return push(Toast(scene: scene, title: title, message: message))
|
||||
@discardableResult func push(toast scene: Toast.Scene, title: String? = nil, message: String? = nil, actions: ((Toast) -> Void)? = nil) -> Toast {
|
||||
let t = Toast(scene: scene, title: title, message: message)
|
||||
actions?(t)
|
||||
t.view.layoutIfNeeded()
|
||||
return push(t)
|
||||
}
|
||||
|
||||
/// 获取指定的toast
|
||||
|
@ -326,8 +333,8 @@ public extension ProHUD {
|
|||
/// - Parameter title: 标题
|
||||
/// - Parameter message: 内容
|
||||
/// - Parameter icon: 图标
|
||||
@discardableResult class func push(toast: Toast.Scene, title: String? = nil, message: String? = nil) -> Toast {
|
||||
return shared.push(toast: toast, title: title, message: message)
|
||||
@discardableResult class func push(toast: Toast.Scene, title: String? = nil, message: String? = nil, actions: ((Toast) -> Void)? = nil) -> Toast {
|
||||
return shared.push(toast: toast, title: title, message: message, actions: actions)
|
||||
}
|
||||
|
||||
/// 获取指定的toast
|
||||
|
|
Loading…
Reference in New Issue