How change .navigationBarTitle font in SwiftUI?

In SwiftUI, at this point we can not change the navigationBarTitle font directly, but you can change navigationBar appearance like this,

struct YourView: View {
    init() {
        //Use this if NavigationBarTitle is with Large Font
        //UINavigationBar.appearance().largeTitleTextAttributes = [.font : UIFont(name: "Georgia-Bold", size: 20)!]

        //Use this if NavigationBarTitle is with displayMode = .inline
        UINavigationBar.appearance().titleTextAttributes = [.font : UIFont(name: "Georgia-Bold", size: 20)!]
    }
    var body: some View {
        NavigationView {
            Text("Hello World!")
            //.navigationBarTitle("TEST")
            .navigationBarTitle (Text("TEST"), displayMode: .inline)
        }
    }
}

I hope it will help you. Thanks!!


I think you have to create a NavigationBarBuilder.

struct NavigationBarBuilder: UIViewControllerRepresentable {

    var build: (UINavigationController) -> Void = { _ in }

    func makeUIViewController(context: UIViewControllerRepresentableContext<NavigationBarBuilder>) -> UIViewController {

        UIViewController()
    }

    func updateUIViewController(_ uiViewController: UIViewController, context: UIViewControllerRepresentableContext<NavigationBarBuilder>) {

        if let navigationController = uiViewController.navigationController{
            self.build(navigationController)
        }
    }
}

and you can use it in your content view.

struct ContentView: View {
    var body: some View {
        NavigationView {
            Text("")
                .navigationBarTitle("Türkiye", displayMode: .inline)
                .background(NavigationBarBuilder {navigationController in
                    navigationController.navigationBar.barTintColor = .red
                    navigationController.navigationBar.titleTextAttributes = [.foregroundColor: UIColor.white]
                })
        }
        .navigationViewStyle(StackNavigationViewStyle())
    }
}

Good luck...


In SwiftUI 5 UINavigationBar.appearance().titleTextAttributes doesn't work. You need to use one of the following to change the font in the title:

        init () {
            UINavigationBar.appearance().largeTitleTextAttributes = [.font : UIFont(name: "Georgia", size: 20)!]
            // OR
            UINavigationBar.appearance().largeTitleTextAttributes = [.font:UIFont.preferredFont(forTextStyle:.text-style)]
        }

where .text-style could be found in UIFont.TextStyle documentation, e.g.

.caption
.body
.title1
.title2
.title3
etc

Update 1 (to answer a qs about exact code in comments)

struct ContentView: View {

    init () {
        let paragraph = NSMutableParagraphStyle()
        paragraph.alignment = .center
        
        UINavigationBar.appearance().largeTitleTextAttributes = [.font:UIFont.preferredFont(forTextStyle:.title2),
                                                                 .foregroundColor:UIColor.systemBlue,
                                                                 .paragraphStyle: paragraph
                                                                ]

...

then in body I have this. You should probably pay attention to displayMode param

// Body is in the same ContentView struct. Settings from init will be used in navigationBarTitle
// listView() is just a custom function returning a SwiftUI's List()

var body: some View {


        NavigationView {
            
        listView()
            .navigationBarTitle(
                Text(self.accts.selCount <= 0 ? "Accounts" : "\(self.accts.selCount) selected")
                ,
                displayMode:.large)

You can't change navigationBarTitle's font with .font modifier yet (Tested in Xcode 11-Beta2).

But you can build your own custom navigationBarView with complete access to any of its subviews like this:

struct NavigationBarView: View {

    var body: some View {

        VStack(spacing: 0) {
            Rectangle()
                .foregroundColor(Style.Color.navigationBarColor)
                .edgesIgnoringSafeArea(.top)
                .frame(height: 0)

            Rectangle()
                .foregroundColor(Style.Color.navigationBarColor)
                .frame(height: 64)
            .overlay(
                HStack() {
                    Image("close")
                    Spacer()

                    Text("سفر به سلامت")
                        .font(Style.Font.navigationTitle)
                        .color(Style.Color.darkTextColor)
                        .multilineTextAlignment(.center)

                    Spacer()
                    Image("menu")
                }
            )

            Spacer()
        }
        .edgesIgnoringSafeArea(.horizontal)
    }
}

Note that you will lose LargeTitleStyle with this implementation.