-
Notifications
You must be signed in to change notification settings - Fork 0
/
iOS_Util.swift
146 lines (133 loc) · 5.27 KB
/
iOS_Util.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
// iOS_Util.Swift
// dbien
// 03DEC2024
// iOS utilities for Swift.
import Foundation
import SpriteKit
import UIKit
// ShareJsonFiles: This shares all json files located in a given directory. THe user can then choose how to share them.
func ShareJsonFiles(fromDirectory logDir: String) {
let fileURLs = try? FileManager.default.contentsOfDirectory(
at: URL(fileURLWithPath: logDir),
includingPropertiesForKeys: nil
).filter { $0.pathExtension == "json" }
guard let urls = fileURLs, !urls.isEmpty else { return }
let activityVC = UIActivityViewController(
activityItems: urls,
applicationActivities: nil
)
if let windowScene = UIApplication.shared.connectedScenes.first as? UIWindowScene,
let rootVC = windowScene.windows.first?.rootViewController
{
rootVC.present(activityVC, animated: true)
}
}
// Translate a string that is in the format "#RRGGBBAA", "#RRGGBB", or a color name to a UIColor
func UIColorFromJSString(_ colorString: String) -> UIColor {
if colorString.hasPrefix("#") {
let hex = String(colorString.dropFirst())
var rgbValue: UInt64 = 0
if !Scanner(string: hex).scanHexInt64(&rgbValue) {
NSLog("Invalid color string format: \(colorString)")
return .black
}
let length = hex.count
if length == 8 { // #RRGGBBAA
return UIColor(
red: CGFloat((rgbValue >> 24) & 0xFF) / 255.0,
green: CGFloat((rgbValue >> 16) & 0xFF) / 255.0,
blue: CGFloat((rgbValue >> 8) & 0xFF) / 255.0,
alpha: CGFloat(rgbValue & 0xFF) / 255.0)
} else if length == 6 { // #RRGGBB
return UIColor(
red: CGFloat((rgbValue >> 16) & 0xFF) / 255.0,
green: CGFloat((rgbValue >> 8) & 0xFF) / 255.0,
blue: CGFloat(rgbValue & 0xFF) / 255.0,
alpha: 1.0)
} else {
NSLog("Invalid color string format: \(colorString)")
return .black
}
}
let colorMap: [String: UIColor] = [
"black": .black,
"blue": .blue,
"brown": .brown,
"cyan": .cyan,
"darkgray": .darkGray,
"gray": .gray,
"green": .green,
"lightgray": .lightGray,
"magenta": .magenta,
"orange": .orange,
"purple": .purple,
"red": .red,
"white": .white,
"yellow": .yellow,
"systemblue": .systemBlue,
"systembrown": .systemBrown,
"systemgreen": .systemGreen,
"systemindigo": .systemIndigo,
"systemorange": .systemOrange,
"systempink": .systemPink,
"systempurple": .systemPurple,
"systemred": .systemRed,
"systemteal": .systemTeal,
"systemyellow": .systemYellow,
"systemgray": .systemGray,
"systemgray2": .systemGray2,
"systemgray3": .systemGray3,
"systemgray4": .systemGray4,
"systemgray5": .systemGray5,
"systemgray6": .systemGray6,
]
return colorMap[colorString.lowercased()] ?? .black
}
// Creates a path that draws 4 lines whose outer edges exactly match the input rectangle
// this eliminates the annoying background showing through a couple of pixels at the very corner
// when just using a rectangle - results in perfectly square corners with any line thickness.
func CreateSquarePathFromRectInner(rect: CGRect, thicknessX: CGFloat, thicknessY: CGFloat = -1)
-> CGPath
{
let halfThickX = thicknessX / 2
let halfThickY = thicknessY < 0 ? halfThickX : thicknessY / 2
let path = CGMutablePath()
path.move(to: CGPoint(x: rect.minX + halfThickX, y: rect.maxY - halfThickY))
path.addLine(to: CGPoint(x: rect.maxX - halfThickX, y: rect.maxY - halfThickY))
path.move(to: CGPoint(x: rect.maxX - halfThickX, y: rect.maxY - halfThickX))
path.addLine(to: CGPoint(x: rect.maxX - halfThickX, y: rect.minY + halfThickX))
path.move(to: CGPoint(x: rect.maxX - halfThickX, y: rect.minY + halfThickY))
path.addLine(to: CGPoint(x: rect.minX + halfThickX, y: rect.minY + halfThickY))
path.move(to: CGPoint(x: rect.minX + halfThickX, y: rect.minY + halfThickX))
path.addLine(to: CGPoint(x: rect.minX + halfThickX, y: rect.maxY - halfThickX))
return path
}
func CreateRectPathFromRectInner(rect: CGRect, thickness: CGFloat) -> CGPath {
let halfThickness = thickness / 2
let innerRect = rect.insetBy(dx: halfThickness, dy: halfThickness)
let path = CGPath(rect: innerRect, transform: nil)
return path
}
public func ConvertLength(_ scene: SKScene, _ length: CGFloat) -> CGFloat {
let origin = scene.convertPoint(fromView: CGPoint.zero)
let point = scene.convertPoint(fromView: CGPoint(x: length, y: 0))
return CGFloat(floor(abs(point.x - origin.x)))
}
// Convert x and y lengths in case they end up diff.
public func ConvertLengths(_ scene: SKScene, _ length: CGFloat) -> (CGFloat, CGFloat) {
let origin = scene.convertPoint(fromView: CGPoint.zero)
let point = scene.convertPoint(fromView: CGPoint(x: length, y: length))
return (CGFloat(floor(abs(point.x - origin.x))), CGFloat(floor(abs(point.y - origin.y))))
}
public func ShowModalAlert(title: String, message: String) {
let alert = UIAlertController(
title: NSLocalizedString(title, comment: ""),
message: NSLocalizedString(message, comment: ""),
preferredStyle: .alert)
alert.addAction(UIAlertAction(title: NSLocalizedString("OK", comment: ""), style: .default))
if let windowScene = UIApplication.shared.connectedScenes.first as? UIWindowScene,
let rootVC = windowScene.windows.first?.rootViewController
{
rootVC.present(alert, animated: true)
}
}