Dunfey · Hotel WWDC as data, est. 1983
Front desk everything
Years
Topics

2020 Swift

WWDC20 · 21 min · Swift

Embrace Swift type inference

Swift uses type inference to help you write clean, concise code without compromising type safety. We’ll show you how the compiler seeks out clues in your code to solve the type inference puzzle. Discover what happens when the compiler can’t come to a solution, and find out how Xcode 12 integrates error tracking to help you understand and fix mistakes at compile time.

Watch at developer.apple.com ↗

Transcript all transcripts

Code shown on screen · 2 snippets

SmoothieList swift · at 2:56 ↗
import SwiftUI

struct SmoothieList: View {
    var smoothies: [Smoothie]
    
    @State var searchPhrase = ""

    var body: some View {
        FilteredList(
            smoothies,
            filterBy: \.title,
            isIncluded: { title in title.hasSubstring(searchPhrase) }
        ) { smoothie in
            SmoothieRowView(smoothie: smoothie)
        }
    }
}

extension String {
    /// Returns `true` if this string contains the provided substring,
    /// or if the substring is empty. Otherwise, returns `false`.
    ///
    /// - Parameter substring: The substring to search for within
    ///   this string.
    func hasSubstring(_ substring: String) -> Bool {
        substring.isEmpty || contains(substring)
    }
}
FilteredList swift · at 3:53 ↗
import SwiftUI

public struct FilteredList<Element, FilterKey, RowContent>: View
        where Element: Identifiable, RowContent: View {

    private let data: [Element]
    private let filterKey: KeyPath<Element, FilterKey>
    private let isIncluded: (FilterKey) -> Bool
    private let rowContent: (Element) -> RowContent

    public init(
        _ data: [Element],
        filterBy key: KeyPath<Element, FilterKey>,
        isIncluded: @escaping (FilterKey) -> Bool,
        @ViewBuilder rowContent: @escaping (Element) -> RowContent
    ) {
        self.data = data
        self.filterKey = key
        self.isIncluded = isIncluded
        self.rowContent = rowContent
    }

    public var body: some View {
        let filteredData = data.filter {
            isIncluded($0[keyPath: filterKey])
        }

        return List(filteredData, rowContent: rowContent)
    }
}

Resources