Extensions.swift 3.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137
  1. //
  2. // String+Extension.swift
  3. // deltachat-ios
  4. //
  5. // Created by Bastian van de Wetering on 03.04.19.
  6. // Copyright © 2019 Jonas Reinsch. All rights reserved.
  7. //
  8. import UIKit
  9. extension String {
  10. func containsCharacters() -> Bool {
  11. return !trimmingCharacters(in: [" "]).isEmpty
  12. }
  13. // O(n) - returns indexes of subsequences -> can be used to highlight subsequence within string
  14. func contains(subSequence: String) -> [Int] {
  15. if subSequence.count > self.count {
  16. return []
  17. }
  18. let str = self.lowercased()
  19. let sub = subSequence.lowercased()
  20. var j = 0
  21. var foundIndexes:[Int] = []
  22. for (index, char) in str.enumerated() {
  23. if j == sub.count {
  24. break
  25. }
  26. if char == sub.subScript(j) {
  27. foundIndexes.append(index)
  28. j += 1
  29. }
  30. }
  31. return foundIndexes.count == sub.count ? foundIndexes : []
  32. }
  33. func subScript(_ i: Int) -> Character {
  34. return self[index(startIndex, offsetBy: i)]
  35. }
  36. func bold(indexes: [Int], fontSize: CGFloat?) -> NSAttributedString {
  37. let attributedText = NSMutableAttributedString.init(string: self)
  38. for index in indexes {
  39. attributedText.addAttribute(.font, value: UIFont.boldSystemFont(ofSize: fontSize ?? 18), range: NSMakeRange(index, 1))
  40. }
  41. return attributedText
  42. }
  43. }
  44. extension URL {
  45. public var queryParameters: [String: String]? {
  46. guard
  47. let components = URLComponents(url: self, resolvingAgainstBaseURL: true),
  48. let queryItems = components.queryItems else { return nil }
  49. return queryItems.reduce(into: [String: String]()) { result, item in
  50. result[item.name] = item.value
  51. }
  52. }
  53. }
  54. extension Dictionary {
  55. func percentEscaped() -> String {
  56. return map { key, value in
  57. let escapedKey = "\(key)".addingPercentEncoding(withAllowedCharacters: .urlQueryValueAllowed) ?? ""
  58. let escapedValue = "\(value)".addingPercentEncoding(withAllowedCharacters: .urlQueryValueAllowed) ?? ""
  59. return escapedKey + "=" + escapedValue
  60. }
  61. .joined(separator: "&")
  62. }
  63. }
  64. extension CharacterSet {
  65. static let urlQueryValueAllowed: CharacterSet = {
  66. let generalDelimitersToEncode = ":#[]@" // does not include "?" or "/" due to RFC 3986 - Section 3.4
  67. let subDelimitersToEncode = "!$&'()*+,;="
  68. var allowed = CharacterSet.urlQueryAllowed
  69. allowed.remove(charactersIn: "\(generalDelimitersToEncode)\(subDelimitersToEncode)")
  70. return allowed
  71. }()
  72. }
  73. extension URLSession {
  74. func synchronousDataTask(request: URLRequest) -> (Data?, URLResponse?, Error?) {
  75. var data: Data?
  76. var response: URLResponse?
  77. var error: Error?
  78. let semaphore = DispatchSemaphore(value: 0)
  79. let task = dataTask(with: request) {
  80. data = $0
  81. response = $1
  82. error = $2
  83. semaphore.signal()
  84. }
  85. task.resume()
  86. _ = semaphore.wait(timeout: .distantFuture)
  87. return (data, response, error)
  88. }
  89. }
  90. extension MRContact {
  91. func contains(searchText text: String) -> [ContactHighlights] {
  92. var nameIndexes = [Int]()
  93. var emailIndexes = [Int]()
  94. let contactString = name + email
  95. let subsequenceIndexes = contactString.contains(subSequence: text)
  96. if !subsequenceIndexes.isEmpty {
  97. for index in subsequenceIndexes {
  98. if index < name.count {
  99. nameIndexes.append(index)
  100. } else {
  101. let emailIndex = index - name.count
  102. emailIndexes.append(emailIndex)
  103. }
  104. }
  105. return [ContactHighlights(contactDetail: .NAME, indexes: nameIndexes), ContactHighlights(contactDetail: .EMAIL, indexes: emailIndexes)]
  106. } else {
  107. return []
  108. }
  109. }
  110. }