From 12eb447febc5a0f25bcb01ec2e56d7b28cde3332 Mon Sep 17 00:00:00 2001 From: Paul Hitt Date: Fri, 11 Sep 2026 12:22:03 -0400 Subject: [PATCH] iPad: only the list tabs split into two columns Home, Messages and Calls are lists that lead to a conversation, which is what a second column is for. Everything else is a single screen, and splitting those went badly: Files and the wallet pushed their unlock screen into a column a third of the width, and the other two thirds said "Pick a conversation" on a tab with no conversations in it. Account did the same. Found in the 13-inch screenshot set. Those tabs now take the whole width, the way a settings screen does on a tablet. Whether a row opens beside the list or on top of it follows whether the right-hand column is actually showing, so a row on a full-width tab cannot open into a column that is not there. Co-Authored-By: Claude Opus 5 --- Sources/Views/MainTabView.swift | 21 +++++++++++++++++++-- 1 file changed, 19 insertions(+), 2 deletions(-) diff --git a/Sources/Views/MainTabView.swift b/Sources/Views/MainTabView.swift index 7a79c8c..ea79734 100644 --- a/Sources/Views/MainTabView.swift +++ b/Sources/Views/MainTabView.swift @@ -18,6 +18,19 @@ struct MainTabView: View { private var isWide: Bool { sizeClass == .regular } + /// Home, Messages and Calls: the tabs that are lists leading to a + /// conversation, which is what a second column is for. + /// + /// Everything else is a single screen. Split, Files and the wallet pushed + /// their unlock screen into a column a third of the width, and the other + /// two thirds said "Pick a conversation" on a tab with no conversations in + /// it. Those take the whole width instead, the way a settings screen does + /// on a tablet. + private static let listTabs: Set = [0, 1, 2] + + /// Two columns only when there is room for two AND this tab is a list. + private var usesSplit: Bool { isWide && Self.listTabs.contains(selection) } + /// When the Calls tab was last opened, so the missed-call badge counts only /// what arrived since. @AppStorage("fnmsg.callsSeenAt") private var callsSeenAt: Double = 0 @@ -36,8 +49,12 @@ struct MainTabView: View { .environmentObject(pane) // One place decides, and everything downstream reads it. See // SplitPane. + .onChange(of: usesSplit, initial: true) { _, split in + // Whether a row opens beside the list or on top of it depends + // on whether the right-hand column is actually showing. + pane.isWide = split + } .onChange(of: isWide, initial: true) { _, wide in - pane.isWide = wide // Coming back to one column, the conversation on the right has // nowhere to be. Dropping it returns to the list rather than // leaving a chat open that nothing on screen points at. @@ -72,7 +89,7 @@ struct MainTabView: View { } @ViewBuilder private var layout: some View { - if isWide { wideLayout } else { tabs } + if usesSplit { wideLayout } else { tabs } } @ViewBuilder private var tabs: some View {