Why does SwiftUI format dates as "2020 M10 27" in navigationTitle?

Viewed 220

I'm using Xcode 12.1 and the iOS 14.1 simulator.

With the simplest possible code using Text.init(_:style:), the date format seems to differ between the nav bar title and the content view:

struct ContentView: View {
  var body: some View {
    NavigationView {
      Text(Date(), style: .date)
        .navigationTitle(
          Text(Date(), style: .date)
        )
    }
  }
}

I'd expect the title and content to look like "October 27, 2020" but the title looks like "2020 M10 27". I've never seen this format before.

Using a custom Formatter with Text.init(_:formatter:) gives the same result:

struct ContentView: View {
  var body: some View {
    let formatter: DateFormatter = {
      let formatter = DateFormatter()
      formatter.dateStyle = .long
      return formatter
    }()
    
    NavigationView {
      Text(Date(), formatter: formatter) // "October 27, 2020"
        .navigationTitle(
          Text(Date(), formatter: formatter) // "2020 M10 27"
        )
    }
  }
}

Finally, pre-formatting the string with Formatter.string(from:) gives the expected result:

import SwiftUI

struct ContentView: View {
  var body: some View {
    let formatter: DateFormatter = {
      let formatter = DateFormatter()
      formatter.dateStyle = .long
      return formatter
    }()

    NavigationView {
      Text(formatter.string(from: Date())) // "October 27, 2020"
        .navigationTitle(
          Text(formatter.string(from: Date())) // "October 27, 2020"
        )
    }
  }
}

What's going on here? Do I really need this workaround in order to display a date in the navigation title?

1 Answers

Yes, unfortunately it looks like a bug.


As a workaround you can create an extension:

extension Text {
    static let dateFormatter: DateFormatter = {
        let formatter = DateFormatter()
        formatter.dateStyle = .long
        return formatter
    }()

    init(date: Date) {
        self.init(Text.dateFormatter.string(from: date))
    }
}

so you have the same amount of code in navigationTitle:

.navigationTitle(
    Text(date: Date())
)
Related