Skip to content

Instantly share code, notes, and snippets.

@SofiaMNC
Last active November 2, 2021 16:13
Show Gist options
  • Star 1 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save SofiaMNC/92c007acdfa6be3e55b52ba66c11f212 to your computer and use it in GitHub Desktop.
Save SofiaMNC/92c007acdfa6be3e55b52ba66c11f212 to your computer and use it in GitHub Desktop.
An example of a back port implementation to facilitate backward compatibility handling in Swift.
//
// Demo.swift
// bedtimefanlite
//
// Created by Sofia Chevrolat on 02/11/2021.
// Inspired by [Dave DeLong's post](https://davedelong.com/blog/2021/10/09/simplifying-backwards-compatibility-in-swift/)
//
// Two small examples of a "backport" implementation to facilitate backward compatibility.
//
// USAGE :
// 1 - extend the type by adding an enum named `Backport`
// 2 - add an enum case matching exactly the signature of the "backported" function
// 3 - add a computed variable in the enum to return the needed value, encapsulating the `if #available` calls.
// 4 - When you're ready to drop support for the older iOS version, remove the relevant enum case.
// The compiler will tell you where to correct the code. You can simply remove the `.Backport.` and the `.variable`
// to get the correct function.
import Foundation
import UIKit
class DemoFontBackPortComplete {
let fontSize: CGFloat = 64
let label = UILabel()
init() {
label.font = UIFont.Backport.monospacedSystemFont(ofSize: fontSize, weight: .regular).font
}
}
class DemoSFBackPortComplete {
let image: UIImage?
init() {
image = UIImage.Backport.`init`(systemName: "some_SF_symbol").image
}
}
// MARK: - Backports (could be placed in a single file)
extension UIFont {
enum Backport {
// case with identical signature to the "backported" function
case monospacedSystemFont(ofSize: CGFloat, weight: UIFont.Weight)
// a variable to return the needed value
var font: UIFont {
switch self {
case .monospacedSystemFont(let fontSize, let fontWeight):
if #available(iOS 13.0, *) {
return UIFont.monospacedSystemFont(ofSize: fontSize, weight: fontWeight)
} else {
return UIFont.monospacedDigitSystemFont(ofSize: fontSize, weight: fontWeight)
}
}
}
}
}
extension UIImage {
enum Backport {
case `init`(systemName: String)
var image: UIImage? {
switch self {
case .`init`(let assetName):
if #available(iOS 13.0, *) {
return UIImage(systemName: assetName)
} else {
return UIImage(named: assetName)
}
}
}
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment