【问题标题】:Aligning views across form sections跨表单部分对齐视图
【发布时间】:2021-06-11 19:32:56
【问题描述】:

我正在 SwiftUI 中创建一个包含多个部分的表单。每个部分包含几个文本字段,每个字段都有一个标签。

我想将文本字段的前缘相互对齐,并与视图的中心对齐。

我可以使用以下方法在一个部分中对齐文本字段的前沿:

extension HorizontalAlignment {
    private struct LeadingEdgeAlignment: AlignmentID {
        /// A custom alignment for leading edges.
        static func defaultValue(in context: ViewDimensions) -> CGFloat {
            context[.leading]
        }
    }

    /// A guide for aligning leading edges.
    static let leadingEdge = HorizontalAlignment(LeadingEdgeAlignment.self)
}

struct ContentView: View {
    var body: some View {
        Form {
            Section(header: Text("Section One")) {
                VStack(alignment: .leadingEdge) {
                    HStack {
                        Text("Primary")
                        TextField("", text: .constant(""))
                            .frame(minWidth: nil, idealWidth: nil, maxWidth: 75, minHeight: nil, maxHeight: nil)
                            .alignmentGuide(.leadingEdge) { $0[HorizontalAlignment.leading] }
                            .textFieldStyle(RoundedBorderTextFieldStyle())
                    }
                    HStack {
                        Text("Secondary")
                        TextField("", text: .constant(""))
                            .frame(minWidth: nil, idealWidth: nil, maxWidth: 75, minHeight: nil, maxHeight: nil)
                            .alignmentGuide(.leadingEdge) { $0[HorizontalAlignment.leading] }
                            .textFieldStyle(RoundedBorderTextFieldStyle())
                    }
                }
            }
            Section(header: Text("Section Two")) {
                VStack(alignment: .leadingEdge) {
                    HStack {
                        Text("Milk")
                        TextField("", text: .constant(""))
                            .frame(minWidth: nil, idealWidth: nil, maxWidth: 75, minHeight: nil, maxHeight: nil)
                            .alignmentGuide(.leadingEdge) { $0[HorizontalAlignment.leading] }
                            .textFieldStyle(RoundedBorderTextFieldStyle())
                    }
                    HStack {
                        Text("Cheesecake")
                        TextField("", text: .constant(""))
                            .frame(minWidth: nil, idealWidth: nil, maxWidth: 75, minHeight: nil, maxHeight: nil)
                            .alignmentGuide(.leadingEdge) { $0[HorizontalAlignment.leading] }
                            .textFieldStyle(RoundedBorderTextFieldStyle())
                    }
                }
            }
        }
    }
}

但是,到目前为止,我创建跨节对齐指南的所有尝试都失败了。

如何跨表单部分对齐视图?

【问题讨论】:

    标签: swift swiftui


    【解决方案1】:

    由于您要分成两半,因此一种方法是使用偶数列。但是你必须处理文本长度的显着差异

    struct AlignedSectionView: View {
        let columns = [GridItem(), GridItem()]
        var body: some View {
            Form {
                Section(header: Text("Section One")) {
                    //Divide the section in half
                    LazyVGrid(columns: columns, alignment: .leadingEdge) {
                        HStack {
                            Text("Primary")
                            //Push the TextField to the Halfway point
                            Spacer()
                            TextField("", text: .constant(""))
                                .frame(minWidth: nil, idealWidth: nil, maxWidth: 75, minHeight: nil, maxHeight: nil)
                                .alignmentGuide(.leadingEdge) { $0[HorizontalAlignment.leading] }
                                .textFieldStyle(RoundedBorderTextFieldStyle())
                        }
                        //Fill in the column
                        Spacer()
                        HStack {
                            Text("Secondary")
                            Spacer()
                            TextField("", text: .constant(""))
                                .frame(minWidth: nil, idealWidth: nil, maxWidth: 75, minHeight: nil, maxHeight: nil)
                                .alignmentGuide(.leadingEdge) { $0[HorizontalAlignment.leading] }
                                .textFieldStyle(RoundedBorderTextFieldStyle())
                        }
                    }
                }
                Section(header: Text("Section Two")) {
                    //Divide the section in half
                    LazyVGrid(columns: columns, alignment: .leadingEdge) {
                        HStack {
                            Text("Milk")
                            //Push the TextField to the Halfway point
                            Spacer()
                            TextField("", text: .constant(""))
                                .frame(minWidth: nil, idealWidth: nil, maxWidth: 75, minHeight: nil, maxHeight: nil)
                                .alignmentGuide(.leadingEdge) { $0[HorizontalAlignment.leading] }
                                .textFieldStyle(RoundedBorderTextFieldStyle())
                        }
                        //Fill in the column
                        Spacer()
                        HStack {
                            Text("Cheesecake")
                                //So it doesnt go to the next line
                                .lineLimit(1)
                            Spacer()
                            TextField("", text: .constant(""))
                                .frame(minWidth: nil, idealWidth: nil, maxWidth: 75, minHeight: nil, maxHeight: nil)
                                .alignmentGuide(.leadingEdge) { $0[HorizontalAlignment.leading] }
                                .textFieldStyle(RoundedBorderTextFieldStyle())
                        }
                    }
                }
            }
            //One way of dealing with the difference in text sizes is to allow the text to get smaller to fit
            .minimumScaleFactor(0.9)
        }
    }
    

    【讨论】:

    • 这让我走上了正轨,谢谢。我调整了您的代码,将标签和文本字段放在不同的列中,以获得我想要的外观。
    【解决方案2】:

    根据lorem ipsum 的回答,我能够使用LazyVGrid 实现我想要的。

    struct ContentView: View {
        let columns = [GridItem(.flexible(), alignment: .trailing), GridItem(.flexible(), alignment: .leading)]
        var body: some View {
            Form {
                Section(header: Text("Section One")) {
                    LazyVGrid(columns: columns) {
                        Text("Primary")
                        TextField("", text: .constant(""))
                            .frame(minWidth: nil, idealWidth: nil, maxWidth: 75, minHeight: nil, maxHeight: nil)
                            .textFieldStyle(RoundedBorderTextFieldStyle())
                        Text("Secondary")
                        TextField("", text: .constant(""))
                            .frame(minWidth: nil, idealWidth: nil, maxWidth: 75, minHeight: nil, maxHeight: nil)
                            .textFieldStyle(RoundedBorderTextFieldStyle())
                    }
                }
                Section(header: Text("Section Two")) {
                    LazyVGrid(columns: columns) {
                        Text("Milk")
                        TextField("", text: .constant(""))
                            .frame(minWidth: nil, idealWidth: nil, maxWidth: 75, minHeight: nil, maxHeight: nil)
                            .textFieldStyle(RoundedBorderTextFieldStyle())
                        Text("Cheesecake")
                        TextField("", text: .constant(""))
                            .frame(minWidth: nil, idealWidth: nil, maxWidth: 75, minHeight: nil, maxHeight: nil)
                            .textFieldStyle(RoundedBorderTextFieldStyle())
                    }
                }
            }
        }
    }
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2012-05-27
      • 2015-10-04
      • 2014-12-14
      • 2018-09-26
      • 1970-01-01
      • 1970-01-01
      • 2019-10-30
      相关资源
      最近更新 更多