
Xcode 26.0 + iOS 26.0 で、NavigationStackのラージタイトルが消えてしまう問題
現在、Xcode 16.4を使用してiOSアプリを開発しており、Xcode 26への移行を見据えて事前調査をおこなっている。そうした中で、Xcode 26.0.1を試していたところ、NavigationStackのLarge Title(ラージタイトル)が表示されなくなる問題を発見した。
この現象は、既存のコードベースでUINavigationBarAppearance
を使用してナビゲーションバーをカスタマイズしている場合に発生する。iOS 26.0で何が変わったのか、どのような回避策があるのかを調査した結果をまとめた。
本記事では、Xcode 26.0とiOS 26.0の組み合わせで発生するNavigationStackのタイトル表示問題と、その解決策を紹介する。同じ問題に悩んでいる開発者の参考になれば幸いだ。
検証環境
- Xcode 26.0.1
- iPhone 17 Pro / iOS 26.0
- iPhone 15 Pro / iOS 18.5
問題の詳細
Xcode 26.0とiOS 26.0の組み合わせで、UINavigationBarAppearance
のbackgroundColor
を使用してナビゲーションバーに背景色を設定すると、Large Titleが背景の裏側に隠れて表示されなくなる。
具体的には以下の条件がすべて揃った場合に発生する。
- Xcode 26.0でビルド
- iOS 26.0で実行
UINavigationBarAppearance
のbackgroundColor
プロパティを使用- NavigationStackでLarge Titleを表示
期待される動作と実際の動作
期待される動作(iOS 18.5での動作):
- Large Titleが正常に表示される
- スクロール時にLarge TitleからSmall Titleへの遷移がスムーズに行われる
- 背景色が適切に適用される
実際の動作(iOS 26.0での動作):
- Large Titleが表示されない(背景の裏に隠れる)
- Small Titleは正常に表示される
- 背景色は適用されるが、タイトルが見えなくなる
問題が発生するコード
以下のコードでは、iOS 18では正常に表示されるが、iOS 26.0ではLarge Titleが消えてしまう。
import SwiftUI
struct ContentView: View {
var body: some View {
NavigationStack {
List {
ForEach(0 ..< 20) { index in
Text("Item \(index)")
}
}
.navigationTitle(Text("タイトル"))
.defaultNavigationBar()
}
}
}
struct CustomNavigationBarModifier: ViewModifier {
init() {
let appearance = UINavigationBarAppearance()
appearance.configureWithOpaqueBackground()
appearance.backgroundColor = .green // ← この設定が問題の原因
appearance.largeTitleTextAttributes = [
.font: UIFont.systemFont(ofSize: 30, weight: .heavy),
.foregroundColor: UIColor.black,
]
appearance.titleTextAttributes = [
.font: UIFont.systemFont(ofSize: 15, weight: .regular),
.foregroundColor: UIColor.black,
]
UINavigationBar.appearance().standardAppearance = appearance
UINavigationBar.appearance().scrollEdgeAppearance = appearance
}
func body(content: Content) -> some View {
content
}
}
extension View {
func defaultNavigationBar() -> some View {
modifier(CustomNavigationBarModifier())
}
}
#Preview {
ContentView()
}
動作の比較
サンプルコードを実行したところ、iOS 26.0 ではLarge Titleが表示されていない。
iOS 18.5 | iOS 26.0 |
---|---|
![]() |
![]() |
![]() |
![]() |
Large Titleが背景の裏に存在している
背景色を半透明にすると、Large Titleが背景の裏側に存在していることがわかった。
struct CustomNavigationBarModifier: ViewModifier {
init() {
let appearance = UINavigationBarAppearance()
appearance.configureWithOpaqueBackground()
// 背景色を半透明にして検証
appearance.backgroundColor = .green.withAlphaComponent(0.8)
appearance.largeTitleTextAttributes = [
.font: UIFont.systemFont(ofSize: 30, weight: .heavy),
.foregroundColor: UIColor.black,
]
appearance.titleTextAttributes = [
.font: UIFont.systemFont(ofSize: 15, weight: .regular),
.foregroundColor: UIColor.black,
]
UINavigationBar.appearance().standardAppearance = appearance
UINavigationBar.appearance().scrollEdgeAppearance = appearance
}
// 以下省略
}
実行したところ下図のようになった。iOS 26.0以降では、Large Titleのレンダリング順序が変更されたようだ。
さらにXcodeのView Hierarchy(ビュー階層を3D表示するデバッグ機能)を使って、実際のビュー配置を確認してみよう。
iOS 18.5でのビュー階層:
「タイトル」のラベルが、緑の背景Viewよりも手前に配置されていることがわかる。
iOS 26.0でのビュー階層:
「タイトル」のラベルが、緑の背景Viewよりも後ろ側に配置されていることがわかる。
このことからNavigationStackの内部実装が変更されたことが確認できる。おそらくiOS 26で実装されたリキッドグラス(Liquid Glass)のエフェクトを実現するために、レイヤー構造が変更されたのだろう。
推測される原因
iOS 26.0では、NavigationStackの内部実装が変更され、UINavigationBarAppearance
のbackgroundColor
を使用した際のレンダリング順序が変わったと推測される。これにより、背景レイヤーがLarge Titleよりも前面に描画されるようになったと考えられる。
解決策
完全に従来通りにはならないが、iOS 26.0以降ではtoolbarBackground
とtoolbarBackgroundVisibility
を使用し、iOS 18以前では従来通りUINavigationBarAppearance
のbackgroundColor
を使用することで回避できる。
前述のContentViewに以下のModifierを適用することで、両OSバージョンで動作するようになる。
struct CustomNavigationBarModifier: ViewModifier {
init() {
let appearance = UINavigationBarAppearance()
appearance.configureWithOpaqueBackground()
if #unavailable(iOS 26.0) {
// iOS 26.0未満でのみbackgroundColorを設定
appearance.backgroundColor = .green
}
appearance.largeTitleTextAttributes = [
.font: UIFont.systemFont(ofSize: 30, weight: .heavy),
.foregroundColor: UIColor.black,
]
appearance.titleTextAttributes = [
.font: UIFont.systemFont(ofSize: 15, weight: .regular),
.foregroundColor: UIColor.black,
]
UINavigationBar.appearance().standardAppearance = appearance
UINavigationBar.appearance().scrollEdgeAppearance = appearance
}
func body(content: Content) -> some View {
if #available(iOS 26, *) {
// iOS 26.0以降はtoolbarBackgroundを使用
content
.toolbarBackgroundVisibility(.visible, for: .navigationBar)
.toolbarBackground(.green, for: .navigationBar)
} else {
content
}
}
}
extension View {
func defaultNavigationBar() -> some View {
modifier(CustomNavigationBarModifier())
}
}
動作確認結果
サンプルコードを実行したところ、iOS 26.0 でもLarge Titleが表示されるようになった。
iOS 18.5 | iOS 26.0 |
---|---|
![]() |
![]() |
![]() |
![]() |
実装のポイント
#unavailable(iOS 26.0)
を使用して、iOS 26.0未満でのみbackgroundColor
を設定#available(iOS 26, *)
を使用して、iOS 26.0以降でのみtoolbarBackground
を使用- これにより、両方のOSバージョンで正常にLarge Titleが表示される
- ただし、iOS 26.0では
toolbarBackground
の制約により、完全に同一の見た目にはならない
まとめ
Xcode 26.0とiOS 26.0の組み合わせで発生するNavigationStackのLarge Title表示問題について調査し、実用的な解決策を見つけることができた。
この問題はApple Developer Forumsでも報告されており、iOS 26.0.1の時点でも未解決である。Appleのバグなのか、意図的な仕様変更なのかは現時点では不明だが、開発者としては何らかの対応が必要となる。
今回の解決策は完璧ではないものの、両OSバージョンで動作するアプリを提供するための実用的なアプローチだと考えている。iOS 26.1 以降のリリースでApple側で修正される可能性もあるため、今後も動向を注視していく必要があるだろう。
同じ問題に悩んでいる開発者の方は、この回避策を試してみてほしい。また、より良い解決策を見つけた場合は、ぜひ共有していただければ幸いである。
参考資料
サンプルコード。
求人情報: クラスメソッドでは iOSエンジニアを募集しています
スターバックスデジタルテクノロジー部では、iOSアプリ開発のできるエンジニアを募集しています。 misc-ios などで、新しいXcode対応についてのアレコレを共有しながら一緒に働いてくれる方の応募をお待ちしております!