Working with Images in Swift (iOS/macOS)
In this article, we will cover the main approaches and tools for working with images in the Apple ecosystem. You will learn how to load, display, process, and save images using built-in Swift frameworks for iOS and macOS. This material will be useful for both beginners and experienced developers.
Key Frameworks for Working with Images
In Swift, there are several key frameworks for working with graphics:
- UIKit (iOS) —
UIImage,UIImageView - AppKit (macOS) —
NSImage,NSImageView - Core Image — filters and processing
- Core Graphics — low-level drawing
- Metal — GPU acceleration for complex operations
- SwiftUI — declarative interface with
Image
Loading and Displaying Images
Let's look at basic examples for both platforms.
iOS (UIKit)
import UIKit
// Loading from assetslet image = UIImage(named: "example")
// Loading from fileif let path = Bundle.main.path(forResource: "photo", ofType: "jpg") { let imageFromFile = UIImage(contentsOfFile: path)}
// Displaying in UIImageViewlet imageView = UIImageView(frame: CGRect(x: 0, y: 0, width: 200, height: 200))imageView.image = imageimageView.contentMode = .scaleAspectFitmacOS (AppKit)
import AppKit
// Loading from assetslet image = NSImage(named: "example")
// Loading from fileif let path = Bundle.main.path(forResource: "photo", ofType: "jpg") { let imageFromFile = NSImage(contentsOfFile: path)}
// Displaying in NSImageViewlet imageView = NSImageView(frame: NSRect(x: 0, y: 0, width: 200, height: 200))imageView.image = imageimageView.imageScaling = .scaleProportionallyUpOrDownSwiftUI (cross-platform)
import SwiftUI
struct ContentView: View { var body: some View { Image("example") .resizable() .aspectRatio(contentMode: .fit) .frame(width: 200, height: 200) }}Image Processing with Core Image
Core Image provides over 200 built-in filters for image processing. Here is an example of applying a sepia tone:
import CoreImage
func applySepiaFilter(to image: UIImage) -> UIImage? { guard let ciImage = CIImage(image: image) else { return nil } let filter = CIFilter(name: "CISepiaTone") filter?.setValue(ciImage, forKey: kCIInputImageKey) filter?.setValue(0.8, forKey: kCIInputIntensityKey) guard let outputImage = filter?.outputImage else { return nil } let context = CIContext() guard let cgImage = context.createCGImage(outputImage, from: outputImage.extent) else { return nil } return UIImage(cgImage: cgImage)}Resizing and Cropping
It is often necessary to resize an image or crop it to the center:
extension UIImage { func resized(to targetSize: CGSize) -> UIImage { let renderer = UIGraphicsImageRenderer(size: targetSize) return renderer.image { _ in self.draw(in: CGRect(origin: .zero, size: targetSize)) } } func croppedToSquare() -> UIImage { let side = min(size.width, size.height) let x = (size.width - side) / 2 let y = (size.height - side) / 2 let cropRect = CGRect(x: x, y: y, width: side, height: side) guard let cgImage = cgImage?.cropping(to: cropRect) else { return self } return UIImage(cgImage: cgImage) }}Saving Images
Let's look at how to save an image to the gallery or to a file: