All blogs / Mobile / iOS / Android
Swift by Sundell
Weekly Swift articles, podcasts and tips by John Sundell
- Posts
- 533 from 18 Jan 2017 to 30 Oct 2026
- Posting
- now and then (4 in the last year)
- Kind
- personal blog
- Feed
- https://swiftbysundell.com/feed.rss
2026 4
2025 7
- Building a design system at Genius Scan
- Deciding between ‘let’ and ‘var’ for Swift struct properties
- Decoding Swift types that require additional data
- Tips and tricks for when using SwiftUI’s ViewBuilder
- Using Swift’s defer keyword within async and throwing contexts
- Modern URL construction in Swift
- Swift by Sundell is back!
2023 2
2022 31
- Podcast: “The evolution of Swift”, with special guest Nick Lockwood
- Podcast: “Swift concurrency in practice”, with special guest Ben Scheirman
- Combining opaque return types with primary associated types
- Podcast: “Responsive and smooth UIs”, with special guest Adam Bell
- Podcast: “Freelancing and WWDC22 highlights”, with special guest Donny Wals
- Podcast: “The role of system design”, with special guest Gui Rambo
- Sponsored: Essential Developer
- Podcast: “What’s new in SwiftUI in iOS 16?”, with special guest Natalia Panferova
- Switching between SwiftUI’s HStack and VStack
- Podcast: “Swift 5.7, generics, and the road to Swift 6”, with special guest Ben Cohen
- Using the ‘some’ and ‘any’ keywords to reference generic protocols in Swift 5.7
- Swift 5.7’s new optional unwrapping syntax
- Rendering SwiftUI views within UITableView or UICollectionView cells on iOS 16
- Podcast: “The evolution of SwiftUI”, with special guest Chris Eidhof
- Swift by Sundell turns five years old today! Here’s what’s next for the website and the podcast
- Podcast: “A framework and an app”, with special guest Simon Støvring
- Type placeholders in Swift
- Podcast: “Accessibility on Apple’s platforms”, with special guest Sommer Panage
- Abstract types and methods in Swift
- Sponsor: Judo
- Basics: Equality
- Basics
- Podcast: “Where is Swift headed in 2022?”, with special guest JP Simard
- Writing testable code when using SwiftUI
- Combining protocols in Swift
- Memory management when using async/await in Swift
- Automatically retrying an asynchronous Swift Task
- Backgrounds and overlays in SwiftUI
- Basics: Loops
- Creating Combine-compatible versions of async/await-based APIs
- Two ways of capturing self strongly within a closure
2021 85
- Podcast: “The 2021 Season Finale”
- Building an asynchronous SwiftUI button
- Podcast: “Custom rendering”, with special guest James Thomson
- New Discover page: Concurrency
- Delaying an asynchronous Swift Task
- Lightweight dependency injection and unit testing using async functions
- Podcast: “Concurrency beyond app development”, with special guest Tim Condon
- What role do Tasks play within Swift’s concurrency system?
- Swift actors: How do they work, and what kinds of problems do they solve?
- Podcast: “Code maintenance”, with special guest Nick Lockwood
- Unit testing Swift code that uses async/await
- Using count vs isEmpty to check whether a collection contains any elements
- Building async and concurrent versions of forEach and map
- Podcast: “Concurrency and Swift-DocC”, with special guest Marin Todorov
- Using Swift’s concurrency system to run multiple tasks in parallel
- Podcast: “UIKit in 2021”, with special guest Ben Scheirman
- Making async system APIs backward compatible
- Swift’s new concurrency system gains backward compatibility in Xcode 13.2
- New Discover page: Generics
- Specialized extensions using generic type constraints
- Building editable lists with SwiftUI
- Which of the SwiftUI APIs introduced in iOS 15 are backward compatible?
- Podcast: “Opportunities for optimization”, with special guest Christian Selig
- Programmatic navigation in SwiftUI
- Podcast: “Building various kinds of editors”, with special guest Marcin Krzyzanowski
- Previewing SwiftUI views in landscape
- Using Combine’s share operator to avoid duplicate work
- New Discover page: Codable
- Codable synthesis for Swift enums
- Sponsor: Paste
- Conditional compilation within Swift expressions
- Podcast: “The magic of Augmented Reality”, with special guest Roxana Jula
- Async sequences, streams, and Combine
- Podcast: “What’s new in Swift 5.5”, with special guest Antoine van der Lee
- Using static protocol APIs to create conforming instances
- Defining dynamic colors in Swift
- Using ‘@unknown default’ within switch statements
- Podcast: “WWDC21, two months later”, with special guest Jordan Morgan
- Throwing and asynchronous Swift properties
- Attaching property wrappers to function arguments
- Podcast: “Cross-platform SwiftUI”, with special guest Malin Sundberg
- Stroking and filling a SwiftUI shape at the same time
- Mutating and non-mutating Swift contexts
- Sponsor: ViRE
- Podcast: “A tower of capabilities”, with special guest Chris Lattner
- Dismissing a SwiftUI modal or detail view
- Optional SwiftUI views
- Calling async functions within a Combine pipeline
- Making SwiftUI views refreshable
- Basics: Availability checks
- Customizing how an external Swift type is encoded or decoded
- Connecting async/await to other Swift code
- Bindable SwiftUI list elements
- Automatic conversions between Double and CGFloat values in Swift 5.5
- Using the MainActor attribute to automatically dispatch UI updates on the main queue
- Podcast: “Structured concurrency”, with special guest Doug Gregor
- First looks at the new APIs and frameworks announced at WWDC21 on WWDC by Sundell & Friends
- A Swift developer’s WWDC dreams - 2021 edition
- Podcast: “An entire spectrum of apps”, with special guest Sean Allen
- Avoiding problematic cases when using Swift enums
- Avoiding having to recompute values within SwiftUI views
- Three ways to render a SwiftUI view in a playground
- Assigning an expression to a variable with the same name
- Introducing Plot Components: A new way to build HTML pages using Swift
- Deciding what DispatchQueue to run a completion handler on
- Controlling the timing of a Combine pipeline
- Using SwiftUI’s frame modifier to resize and align views
- Styling localized strings in Swift
- A deep dive into Swift’s result builders
- Annotating properties with result builder attributes
- Exploring some of the lesser-known, built-in Formatter types
- Using Combine’s futures and subjects
- Questions
- Automatic handling of property wrapper default values
- Ignoring invalid JSON elements when using Codable
- Unit testing Combine-based Swift code
- Chained implicit member expressions in Swift 5.4
- Managing self and cancellable references when using Combine
- Passing methods as SwiftUI view actions
- Applying rounded corners to a UIKit or SwiftUI view
- Accessing a Swift property wrapper’s enclosing instance
- Avoiding SwiftUI’s AnyView
- Validating email addresses using RawRepresentable and NSDataDetector
- Performing POST and file upload requests using URLSession
- Creating custom query functions using key paths
2020 98
- Using multiple computed properties to form a SwiftUI view’s body
- Welcome to Swift by Sundell 3.0
- 200 weeks of Swift
- The lifecycle and semantics of a SwiftUI view
- Observing Combine publishers in SwiftUI views
- Sorting Swift collections
- Statically computed default property values
- Extending Combine with convenience APIs
- SwiftUI and UIKit interoperability - Part 2
- Creating custom SwiftUI container views
- SwiftUI and UIKit interoperability - Part 1
- Formatting numbers in Swift
- Connecting and merging Combine publishers in Swift
- The power of extensions in Swift
- Publishing constant values using Combine
- Handling loading states within SwiftUI views
- Lazy property observers
- Testing networking logic in Swift
- Importing interactive UIKit views into SwiftUI
- Encapsulating SwiftUI view styles
- Creating generic networking APIs in Swift
- Creating closure-based UI controls using UIAction
- How Swift 5.3 enhances SwiftUI’s DSL
- Building modern collection views in Swift
- Showing view controllers, rather than pushing them
- Working with files and folders in Swift
- Handling view controllers that have custom initializers
- Building SwiftUI debugging utilities
- Using compiler directives in Swift
- How the raw values of Int-based enums get incremented
- Multiline string literal tips and tricks
- Rendering textured views with SwiftUI
- Adding SwiftUI’s ViewBuilder attribute to functions
- Building custom Combine publishers in Swift
- Generating automatic placeholders for SwiftUI views
- Five powerful, yet lesser-known ways to use Swift enums
- SwiftUI extensions using generic type constraints
- Opaque return types in Swift
- Implicit capturing of self in Swift 5.3
- Type inference
- Using an AppDelegate with the new SwiftUI-based app lifecycle
- A guide to SwiftUI’s state management system
- Learning SwiftUI by building tools and prototypes
- A first look at SwiftUI’s new StateObject property wrapper
- A Swift developer’s WWDC dreams - 2020 edition
- Organizing default argument values
- Useful APIs when writing scripts and tools in Swift
- Annotating properties with default decoding values
- Handling model variants in Swift
- Designing reusable Swift libraries
- Quickly replacing singletons with functions
- Getting the most out of Xcode Previews for SwiftUI
- Properties
- Why does Swift by Sundell not use any client-side JavaScript?
- Avoiding deeply nested Swift code
- Building an Observable type for SwiftUI views
- Using test assertion messages as comments
- Propagating user-facing errors in Swift
- Three years of Swift by Sundell
- The different categories of Swift protocols
- Inferred generic type constraints
- Querying collections in Swift
- Enums with custom raw types
- Mixing enums with other Swift types
- Combine
- Published properties in Swift
- Combining dynamic member lookup with key paths
- Handling keyUp and keyDown events on iOS 13.4 and later
- A guide to the SwiftUI layout system - Part 3
- Protocols
- A guide to the SwiftUI layout system - Part 2
- Inline wrapping of UIKit or AppKit views within SwiftUI
- Explicit type annotations
- A guide to the SwiftUI layout system - Part 1
- Making properties overridable only in debug builds
- The Result Type
- When can a struct’s memberwise initializer be used?
- Writing small utility functions in Swift
- Working remotely
- Avoiding massive SwiftUI views
- Using Swift’s built-in randomization APIs
- Splitting up Swift types
- What makes code “Swifty”?
- Using SwiftUI’s ForEach with raw values
- Configuring SwiftUI views
- Optionals
- Exploring Swift 5.2’s new functional features
- Passing key paths as functions
- Picking between a for loop and forEach
- Slicing Swift collections
- Swift’s closure capturing mechanics
- Result’s convenience APIs
- Under the hood of Futures and Promises in Swift
- Property wrappers in Swift
- Test assertions in Swift
- Access Control
- Using Self to refer to enclosing types
- Writing reusable Swift extensions
2019 104
- The Decade of Swift
- Initializers in Swift
- Maintaining model consistency in Swift
- Predicates in Swift
- Making Swift code extensible through plugins
- Lightweight API design in Swift
- Defining custom patterns in Swift
- Combining value and reference types in Swift
- Enums
- Implementing throwing protocol functions as non-throwing
- Deciding whether to adopt new Swift technologies
- Pragmatic unit testing in Swift
- Using key paths in switch statements
- Default arguments in Swift
- Omitting the return keyword
- Encapsulating configuration code in Swift
- Alternatives to protocols in Swift
- Computing dates in Swift
- Making types expressible by string interpolation
- Closures
- 5 small but significant improvements in Swift 5.1
- Gathering test coverage in Xcode
- Managing dependencies using the Swift Package Manager
- SwiftUI
- Reducers in Swift
- Limiting collection mutations
- Picking the right data structure in Swift
- Extracting subsequences
- Caching in Swift
- Referring to overloaded functions
- The power of subscripts in Swift
- Switching on multiple values
- Computed properties in Swift
- Time Complexity
- Computed properties vs methods
- Phantom types in Swift
- Strings
- Passing operators as functions
- Rule-based logic in Swift
- Character category properties
- Utilizing value semantics in Swift
- Specializing generics with type aliases
- Map, FlatMap and CompactMap
- Generalizing Swift code
- Customizing Codable types in Swift
- Default enum associated values
- Defining testing data in Swift
- The power of variadic parameters
- Configurable types
- Improved compiler errors for auto-synthesized conformances in Xcode 11
- Configurable types in Swift
- Improved memberwise initializers in Swift 5.1
- Shifting paradigms in Swift
- Using SwiftUI in a playground
- The Swift 5.1 features that power SwiftUI’s API
- Stacking views in SwiftUI
- Refactoring SwiftUI views using functions
- SwiftUI mix and match
- SwiftUI is a game changer
- A Swift developer’s WWDC dreams - 2019 edition
- Review: Swift Playgrounds 3.0 for iPad
- Extracting view controller actions in Swift
- Functional networking
- Testing custom Codable implementations
- Wrapping sequences in Swift
- Pure functions in Swift
- Structuring model data in Swift
- Generics
- Property observers in Swift
- Refactoring enums which cases contain the same data
- Converting between String and Data without optionals
- Designing Swift APIs
- Combined Swift packages
- String literals in Swift
- Value and Reference Types
- Bindable values in Swift
- Swift’s composition operator
- Memory Management
- Generic algorithms
- Different flavors of type erasure in Swift
- The ‘final’ keyword
- String parsing in Swift
- Using key paths to create convenience APIs
- Error Handling
- Integration tests in Swift
- Recursive enums with “fake” cases
- The power of UserDefaults in Swift
- Pattern matching in Swift
- The flexible syntax of enums
- Inline types and functions in Swift
- Grouping throwing expressions using tuples
- Animations
- Reflection in Swift
- Task-based concurrency in Swift
- Testing error code paths in Swift
- The power of type aliases in Swift
- Codable
- Networking
- Sharing Swift code
- Unit Testing
- Child View Controllers
- Grand Central Dispatch
- Layout Anchors
- Functional networking in Swift
2018 106
- Wrapping up 2018 on Swift by Sundell
- Swift playgrounds tips and tricks
- Slot-based UI development in Swift
- Using property observers
- Using errors as control flow in Swift
- Checking whether an element was inserted into a set
- Mock-free unit tests in Swift
- Managing objects using Locks and Keys in Swift
- Extending optionals in Swift
- Making async tests faster and more stable
- Building iPad Pro features in Swift
- Adding support for Apple Pencil double-taps
- Avoiding race conditions in Swift
- The power of key paths in Swift
- Combining values with functions
- Dependency injection using functions
- Specializing protocols in Swift
- Using a custom exception handler
- Using type aliases to give semantic meaning to primitives
- Building DSLs in Swift
- Specializing protocols using constraints
- Constructing URLs in Swift
- Unwrapping an optional or throwing an error
- Different flavors of view models in Swift
- Testing code that uses static APIs
- Async/await in Swift unit tests
- Reusable data sources in Swift
- Matching multiple enum cases with associated values
- Lightweight presenters in Swift
- Early returning functions in Swift
- Multiline string literals don’t require quotes to be escaped
- Enum iterations in Swift
- Model controllers in Swift
- Reducing sequences
- Avoiding manual Codable implementations
- Trimming long argument lists in Swift
- Type inference-powered serialization in Swift
- Structuring Swift code
- Writing backward compatible Swift code
- Using feature flags instead of feature branches
- Lightweight data hierarchies using tuples
- Refactoring Swift code for testability
- Subclass-free view controllers in Swift
- Custom container view controllers in Swift
- The rule of threes
- Handling mutable models in Swift
- The power of Result types in Swift
- Making Swift tests easier to debug
- Faster & more robust tests with Xcode 10
- Getting started with signposts
- Useful Codable extensions
- Synthesized conditional conformances in Swift 4.2
- A more Swifty Core Animation
- A first look at the Natural Language framework
- Static factory methods in Swift
- Using shared UserDefaults suites
- Writing self-documenting Swift code
- Custom UIView backing layers
- Auto-Equatable enums with associated values
- Launch arguments in Swift
- Defaults for associated types
- Type-safe identifiers in Swift
- Creating a dedicated identifier type
- Logic controllers in Swift
- Assigning optional tuple members to variables
- Delegation in Swift
- Struct convenience initializers
- Usages of throwing functions
- Observers in Swift - Part 2
- Observers in Swift - Part 1
- Nested generic types
- Using the builder pattern in Swift
- Equatable and Hashable structures
- Conditional conformances in Swift
- Conditional conformances
- Generic type aliases
- Feature flags in Swift
- Preventing views from being model aware in Swift
- Parsing command line arguments using UserDefaults
- Using tuples as lightweight types in Swift
- Capturing multiple values in mocks
- The power of sets in Swift
- Code encapsulation in Swift
- Reducing the need for mocks
- Using "then" as an external parameter label for closures
- Navigation in Swift
- Combining lazily evaluated sequences with the builder pattern
- Unit testing asynchronous Swift code
- Faster and more stable UI tests
- Custom operators in Swift
- Accessing the clipboard from a Swift script
- Composing types in Swift
- Throwing tests and LocalizedError
- The difference between static and class properties
- Creating extensions with static factory methods
- Transforming collections in Swift
- Child view controller auto-resizing
- Using zip
- Mocking in Swift
- Defining custom option sets
- Using the where clause with associated types
- Using first class functions when iterating over a dictionary
- First class functions in Swift
- Calling instance methods as static functions
- Dropping suffixes from method names to support multiple arguments
- Constraining protocols to classes to ensure mutability
2017 96
- Wrapping up 2017 on Swift by Sundell
- Goals
- String-based enums in string interpolation
- Separation of concerns using protocols in Swift
- Expressively comparing a value with a list of candidates
- UIView bounds and transforms
- Different flavors of dependency injection in Swift
- UIKit default arguments
- UI testing analytics code in Swift
- Avoiding Massive View Controllers
- Extending optionals
- Building an enum-based analytics system in Swift
- Using where with for-loops
- Using unit tests to identify and avoid memory leaks in Swift
- Using child view controllers as plugins in Swift
- Variable shadowing
- Using dot syntax for static properties and initializers
- Calling functions as closures with a tuple as parameters
- Avoiding force unwrapping in Swift unit tests
- Productivity
- Enabling static dependency injection
- Dependency injection using factories in Swift
- Type inference for lazy properties in Swift
- Using tokens to handle async Swift code
- Converting Swift errors to NSError
- Capturing objects in Swift closures
- Open sourcing Swift code
- Avoiding singletons in Swift
- Making UIImage macOS compatible
- Using generic type constraints in Swift
- Internally mutable protocol-oriented APIs
- The power of switch statements in Swift
- Creating custom collections in Swift
- Under the hood of Assertions in Swift
- Switching on a set
- Using the factory pattern to avoid shared state in Swift
- Core Animation gems: Using replicator layers in Swift
- Adding the current locale to cache keys
- Setting up tests to avoid retain cycles with weak references
- Replacing legacy code using Swift protocols
- Organizing code using extensions
- Using map to transform an optional into a Result type
- Assigning to self in struct initializers
- Recursively calling closures as inline functions
- Reducing flakiness in Swift tests
- Passing self to required Objective-C dependencies
- Building a declarative animation framework in Swift - Part 2
- Making weak or lazy properties readonly
- Building a declarative animation framework in Swift - Part 1
- Defining static URLs using string literals
- Identifying objects in Swift
- Manipulating points, sizes and frames using math operators
- Using closure types in generic constraints
- Writing end-to-end JSON mapping tests in Swift
- Modelling state in Swift
- Using associated enum values to avoid state-specific optionals
- Using SpriteKit to create animations in Swift
- Using enums for async result types
- Writing unit tests in Swift playgrounds
- Working on async code in a playground
- Overriding self with a weak reference
- Exploring the new String API in Swift 4
- A deep dive into Grand Central Dispatch in Swift
- Using DispatchWorkItem
- Using @autoclosure when designing Swift APIs
- Getting started with Xcode UI testing in Swift
- Combining a sequence of functions
- Chaining optionals with map and flatMap
- Using lazy properties in Swift
- Using self-executing closures for lazy properties
- Adding Continuous Integration to a Swift project
- Picking the right way of failing in Swift
- Time traveling in Swift unit tests
- Avoiding mocking UserDefaults
- Using variadic parameters
- Building a command line tool using the Swift Package Manager
- Handling non-optional optionals in Swift
- Referring to enum cases with associated values as closures
- Namespacing Swift code with nested types
- Comparing objects by instance
- Calling initializers with dot syntax and passing them as closures
- Testing Swift code that uses system singletons in 3 easy steps
- Structuring UI tests as extensions on XCUIApplication
- Avoiding default cases in switch statements
- Using the guard statement in different scopes
- Simple Swift dependency injection with functions
- Using #function for UserDefaults key consistency
- Improving Swift compile times
- Using a name already taken by the standard library
- Swift sequences: The art of being lazy
- Type erasure using closures in Swift
- Providing a unified Swift error API
- Using typealiases to reduce the length of method signatures
- Referencing either external or internal parameter names when writing docs
- Using auto closures
- Namespacing with nested types