【问题标题】:Make TextField wrap it content in SwiftUI让 TextField 在 SwiftUI 中包装它的内容
【发布时间】:2020-05-15 11:16:36
【问题描述】:

我正在尝试实现这样的组件

TextField (5 000) 和 Text (PLN) 一起应该水平居中。输入新数字时,应关闭文本 (PLN)。我想我必须将这两个视图合并到一个容器中并居中,类似于

HStack {
   TextField()
   Text("PLN")
}
.frame(alignment: .center)

但 TextField 占用了所有可能的宽度。

我该如何处理它,或者可能是另一种解决方案。

【问题讨论】:

  • “在输入新数字时,应关闭文本 (PLN)”是什么意思。是否应该在 TextField 中包含超过 4 个字符时将其关闭,或者在您输入 TextField 时将其关闭...?
  • 想象一下,这是一个单视图 5000PLN,它可以有不同的长度,但应该始终居中。

标签: ios swift swiftui


【解决方案1】:

这是使用动态大小的TextField 的可能方法。

注意:助手 rectReader 取自 this 我的帖子。

使用 Xcode 11.4 / iOS 13.4 测试(黑边仅用于演示)

struct DemoCenterTextField: View {
    @State private var value = ""
    @State private var frame = CGRect.zero

    var body: some View {
        return HStack(alignment: .bottom) {
            ZStack {
                Text(self.value).foregroundColor(Color.clear)
                    .fixedSize()
                    .background(rectReader($frame))

                TextField("#.#", text: $value)
                    .multilineTextAlignment(.trailing)
                    .frame(minWidth: 80, idealWidth: frame.width)
                    .fixedSize(horizontal: true, vertical: false)
                    .border(Color.black)      // << for demo only

            }.font(Font.system(size: 40).bold())

            Text("PLN")
        }
    }
}

【讨论】:

  • 很棒的答案。我一直在寻找那个。谢谢
  • @Asperi 但是 .frame(minWidth: 80, IdealWidth: frame.width) 导致约束错误“指定了矛盾的框架约束”。你知道如何避免吗?
  • @Konstantin.Efimenko,这只是一个演示,有最小限制,但如果想继续使用它,可以使用 .frame(minWidth: 80, idealWidth: max(frame.width, 80)) 之类的东西(其中可以将最小值设置为常量以避免魔法数字)。
【解决方案2】:

您可以根据 TextField 中的字符数量来设置帧大小,以达到您想要的效果:

struct ContentView: View {
    @State private var textField = ""

    var body: some View {

        HStack {
            TextField("", text: $textField)
                .frame(width: CGFloat(textField.count+10)*5, height: nil)
                .textFieldStyle(RoundedBorderTextFieldStyle()) // Just to illustrate the field better.
                .multilineTextAlignment(.center)
            Text("PLN")
                .offset(x: -15, y:0)
        }
    }
}

【讨论】:

  • 这也是我最初的想法,但字符有不同的宽度,比如“。”和“8”
  • Asperis 上面的答案是一种不同的平滑方法。 :-)
猜你喜欢
  • 1970-01-01
  • 2021-08-28
  • 1970-01-01
  • 1970-01-01
  • 2015-12-06
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多