You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何创建含多组嵌套列表、可整体滚动的SwiftUI侧边栏?

解决SwiftUI侧边栏DisclosureGroup嵌套列表的滚动与展开问题

问题描述

我想要创建一个包含多个DisclosureGroup的侧边栏,其中部分DisclosureGroup包含嵌套列表。侧边栏完全展开后长度会超过屏幕,因此需要支持整体滚动。

当前代码存在以下问题:

  • Section 2可正常展开,但Section 1完全无法展开;
  • 给Section 3设置固定frame可显示嵌套列表,但会出现滚动嵌套的情况,且frame无法随展开的嵌套列表自适应调整。

目标是实现一个包含三个DisclosureGroup的侧边栏,支持折叠、展开并作为整体单元滚动。

问题代码

import SwiftUI

class MenuItem: Identifiable {
    var id = UUID()
    var text : String
    var children : [MenuItem]? = [MenuItem]()
    
    init(text: String) {
        self.text = text
    }
}

struct ContentView: View {
    
    var menuItems = [MenuItem]()
    
    init() {
        for itemText in ["One", "Two", "Three", "Four", "Five"] {
            menuItems.append(MenuItem(text: itemText))
        }
        for item in menuItems {
            for childText in ["A", "B", "C", "D", "E"] {
                item.children?.append(MenuItem(text: childText))
            }
        }
    }
        
    var body: some View {
        ScrollView {
            DisclosureGroup("Section 1") {
                List(menuItems, children: \.children) { item in
                    Text(item.text)
                }            }
            DisclosureGroup("Section 2") {
                Text("Some other stuff")
            }
            DisclosureGroup("Section 3") {
                List(menuItems, children: \.children) { item in
                    Text(item.text)
                }.frame(minHeight: 300)
            }
        }
    }
}

struct ContentView_Previews: PreviewProvider {
    static var previews: some View {
        ContentView()
    }
}

解决方案

问题核心在于List自带滚动特性,与外层ScrollView产生冲突,且默认会占满可用空间,导致DisclosureGroup无法正确计算展开高度。改用OutlineGroup替代List即可解决——它专门用于展示层级数据,无内置滚动,能完美适配DisclosureGroup的折叠展开逻辑,配合外层ScrollView实现整体滚动。

修改后的代码如下:

import SwiftUI

class MenuItem: Identifiable {
    var id = UUID()
    var text : String
    var children : [MenuItem]? = [MenuItem]()
    
    init(text: String) {
        self.text = text
    }
}

struct ContentView: View {
    
    var menuItems = [MenuItem]()
    
    init() {
        for itemText in ["One", "Two", "Three", "Four", "Five"] {
            menuItems.append(MenuItem(text: itemText))
        }
        for item in menuItems {
            for childText in ["A", "B", "C", "D", "E"] {
                item.children?.append(MenuItem(text: childText))
            }
        }
    }
        
    var body: some View {
        ScrollView {
            VStack(alignment: .leading, spacing: 0) {
                DisclosureGroup("Section 1") {
                    OutlineGroup(menuItems, children: \.children) { item in
                        Text(item.text)
                            .padding(.vertical, 8)
                            .padding(.leading, 20)
                    }
                }
                .padding(.vertical, 4)
                
                DisclosureGroup("Section 2") {
                    Text("Some other stuff")
                        .padding(.vertical, 8)
                        .padding(.leading, 20)
                }
                .padding(.vertical, 4)
                
                DisclosureGroup("Section 3") {
                    OutlineGroup(menuItems, children: \.children) { item in
                        Text(item.text)
                            .padding(.vertical, 8)
                            .padding(.leading, 20)
                    }
                }
                .padding(.vertical, 4)
            }
            .padding()
        }
        .frame(width: 250) // 侧边栏固定宽度,可按需调整
    }
}

struct ContentView_Previews: PreviewProvider {
    static var previews: some View {
        ContentView()
    }
}

关键修改点

  • 替换List为OutlineGroup:OutlineGroup仅负责渲染层级结构,无内置滚动,能跟随DisclosureGroup的展开自动调整高度;
  • 添加内边距:给列表项和DisclosureGroup设置合适内边距,模拟原生List的视觉体验;
  • 用VStack统一包裹:让所有DisclosureGroup垂直排列,确保外层ScrollView能将整个侧边栏作为单一滚动单元。

修改后所有DisclosureGroup均可正常折叠展开,侧边栏整体滚动流畅,嵌套列表高度会自动适配内容,无滚动嵌套问题。

内容的提问来源于stack exchange,提问作者Ductcoder

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.29 12:23:28