import SwiftUI

/// T-iPad-2 · regular 宽度（iPad 全屏 / 大分屏 / Stage Manager 大窗）的分栏根
/// 视图。左 sidebar = 会话列表（复用 `SessionListScreen` **不改一行** + 与
/// stack 同款的「项目」leading 工具栏入口）；右 detail = `TerminalContainerView`
/// （终端 + gate/digest 叠层，复用不动），无打开会话时给「选择或新建会话」占位。
///
/// 设计要点：
/// - **detail 复用 `TerminalContainerView`**：终端组装与它挂 push destination 还是
///   split detail 无关，只换外层容器、内容零改（PLAN_IOS_IPAD §1）。
/// - **选中态经 `AppCoordinator` 单一真值**：sidebar 触发面全部走
///   `selectSidebarItem` / `open`（同 stack 的既有路由），不新开会话生命周期。
///   `coordinator.sidebarSelection` 提供二向绑定；行 highlight 需 sidebar List
///   采纳 `selection:`（`SessionListScreen` 的 List，属列表组 Owns），见文末注。
/// - **detail 终端仍带 `.id(controller.id)`**：换会话时新 controller → 新
///   SwiftTerm 视图（回放 ring buffer），identity 稳定复用 T-iOS-29 语义。
/// - **隐私遮罩不在这里**：它在 `AdaptiveRootView` 的 ZStack 顶层，两分支共享，
///   故 detail 终端字节同样在 `scenePhase != .active` 时被遮（安全不变式）。
/// - **视觉层**：横幅/占位/工具栏全部走冻结 `DS.*` token 与共享 Primitive，
///   与 stack 分支像素级一致（继续横幅、项目入口都是同一组件）。
struct SplitRootView: View {
    @Bindable var coordinator: AppCoordinator
    @Environment(\.accessibilityReduceMotion) private var reduceMotion

    var body: some View {
        NavigationSplitView {
            sidebar
        } detail: {
            detail
        }
    }

    // MARK: - Sidebar（会话列表 + 项目入口，复用 SessionListScreen）

    private var sidebar: some View {
        SessionListScreen(
            viewModel: coordinator.sessionList,
            onOpen: { request in
                // 分栏只是又一个触发面：映射到同一 selectSidebarItem 路由。
                coordinator.selectSidebarItem(sidebarItem(for: request))
            },
            onAddHost: { coordinator.presentAddHost() },
            onDeviceCert: { coordinator.presentDeviceCert() },
            onEnroll: { coordinator.presentEnrollment() }
        )
        .safeAreaInset(edge: .bottom) { continueLastBanner }
        .animation(
            DS.Motion.gated(DS.Motion.base, reduceMotion: reduceMotion),
            value: coordinator.continueLastSessionId
        )
        .toolbar { ProjectsToolbarItem(coordinator: coordinator) }
    }

    /// 与 stack 底栏同款「继续上次会话」（冷启动第 5 步）—— 复用共享
    /// `ContinueLastBanner`，iPad 用户不丢该入口（T-iPad-5 finding）。
    @ViewBuilder private var continueLastBanner: some View {
        if coordinator.continueLastSessionId != nil {
            ContinueLastBanner { coordinator.openContinueLast() }
                .transition(.move(edge: .bottom).combined(with: .opacity))
        }
    }

    /// 列表的 `OpenRequest` → sidebar 选中项（sessionId 有无 = 采纳既有 / 新建）。
    private func sidebarItem(for request: SessionListViewModel.OpenRequest) -> SidebarItem {
        request.sessionId.map(SidebarItem.session) ?? .newSession
    }

    // MARK: - Detail（终端或占位）

    @ViewBuilder private var detail: some View {
        if let controller = coordinator.terminalController {
            NavigationStack {
                TerminalContainerView(
                    controller: controller,
                    onNewSessionInCwd: { coordinator.openNewSessionInCurrentCwd() },
                    onKillSession: { coordinator.killCurrentSession() } // T-iPad-3
                )
                .id(controller.id) // T-iOS-29 · identity per controller
            }
        } else {
            placeholder
                .transition(.opacity)
        }
    }

    /// 空 detail 占位 —— accent 图标 + 邀约式文案（DS 方向：ContentUnavailableView
    /// + 好符号 + 友好中文）。图标着 accent 靛紫，与全 App 强调色呼应。
    private var placeholder: some View {
        ContentUnavailableView {
            Label {
                Text(SplitCopy.placeholderTitle)
            } icon: {
                Image(systemName: "terminal")
                    .foregroundStyle(DS.Palette.accent)
            }
        } description: {
            Text(SplitCopy.placeholderHint)
        }
    }
}

/// split 专属用户可见文案（「项目」/「继续」标签复用 `RootCopy`，DRY）。
private enum SplitCopy {
    static let placeholderTitle = "选择或新建会话"
    static let placeholderHint = "从左侧选择一个运行中的会话，或新建一个开始工作。"
}
