SwiftUI在多个HStacks中对齐不同长度的文本

Posted

技术标签:

【中文标题】SwiftUI在多个HStacks中对齐不同长度的文本【英文标题】:SwiftUI aligning text with different length in multiple HStacks 【发布时间】:2020-11-21 23:44:29 【问题描述】:

我正在尝试在两个不同的 HStack 中对齐文本,但很难让第二个(较短的长度)与第一个 HStack 对齐。我尝试过使用 .frame(minWidth:0, maxWidth: .infinity)Spacer(),但找不到解决方案。这可能吗?

struct ContentView: View 
var body: some View 
    VStack(alignment: .leading) 
        HStack 
            Spacer()
            Text("Lorem ipsum dolor")
                .font(.system(size: 22, weight: .ultraLight, design: .rounded))
            Spacer()
        .padding()
        .overlay(
            Rectangle()
                .stroke(Color(#colorLiteral(red: 0.6000000238, green: 0.6000000238, blue: 0.6000000238, alpha: 1)), style: StrokeStyle(lineWidth: 0.5, dash: [5.0])))
       
        
        HStack 
            Spacer()
            Text("Lorem ipsum")
                .font(.system(size: 22, weight: .ultraLight, design: .rounded))
            Spacer()
        .padding()
        .overlay(
            Rectangle()
                .stroke(Color(#colorLiteral(red: 0.6000000238, green: 0.6000000238, blue: 0.6000000238, alpha: 1)), style: StrokeStyle(lineWidth: 0.5, dash: [5.0])))
    
  

我尝试使用 Horizo​​ntalAlignment 指南,但它们偏离了中心:

struct ContentView: View 
var body: some View 
    VStack(alignment: .controlLeadingEdge) 
        HStack 
            Text("Lorem ipsum dolor")
                .font(.system(size: 22, weight: .ultraLight, design: .rounded))
                .alignmentGuide(.controlLeadingEdge, computeValue:  d in d[HorizontalAlignment.leading] )
        .padding()
        .frame(minWidth: 0, maxWidth: 300)
        .overlay(
            Rectangle()
                .stroke(Color(#colorLiteral(red: 0.6000000238, green: 0.6000000238, blue: 0.6000000238, alpha: 1)), style: StrokeStyle(lineWidth: 0.5, dash: [5.0])))
        
        HStack 
            Text("Lorem ipsum")
                .font(.system(size: 22, weight: .ultraLight, design: .rounded))
                .alignmentGuide(.controlLeadingEdge, computeValue:  d in d[HorizontalAlignment.leading] )
        .padding()
        .frame(minWidth: 0, maxWidth: 300)
        .overlay(
            Rectangle()
                .stroke(Color(#colorLiteral(red: 0.6000000238, green: 0.6000000238, blue: 0.6000000238, alpha: 1)), style: StrokeStyle(lineWidth: 0.5, dash: [5.0])))
        
    
 


extension HorizontalAlignment 
private enum ControlAlignment: AlignmentID 
    static func defaultValue(in context: ViewDimensions) -> CGFloat 
        return context[HorizontalAlignment.controlLeadingEdge]
    

static let controlLeadingEdge = HorizontalAlignment(ControlAlignment.self)

【问题讨论】:

您希望它如何对齐?你想让最长的一个居中,另一个与最长的前缘对齐吗?第二个总是更短吗? @vacawama 我想让最短的与最长的前缘对齐。是的,这是正确的,第二个也会更短。谢谢 【参考方案1】:

这是一种方法:

重复第一个文本,给它.opacity(0) 并把它放在ZStack.leading 对齐

struct ContentView: View 
    var body: some View 
        let firstText = Text("Loren ipsum dolor")
        let secondText = Text("Loren ipsum")
        
        VStack(alignment: .leading) 
            HStack 
                Spacer()
                firstText
                    .font(.system(size: 22, weight: .ultraLight, design: .rounded))
                Spacer()
            .padding()
            .overlay(
                Rectangle()
                    .stroke(Color(#colorLiteral(red: 0.6000000238, green: 0.6000000238, blue: 0.6000000238, alpha: 1)), style: StrokeStyle(lineWidth: 0.5, dash: [5.0])))
            
            HStack 
                Spacer()
                ZStack(alignment: .leading) 
                    firstText.opacity(0)
                    secondText
                
                .font(.system(size: 22, weight: .ultraLight, design: .rounded))
                Spacer()
            .padding()
            .overlay(
                Rectangle()
                    .stroke(Color(#colorLiteral(red: 0.6000000238, green: 0.6000000238, blue: 0.6000000238, alpha: 1)), style: StrokeStyle(lineWidth: 0.5, dash: [5.0])))
        
    

【讨论】:

非常感谢!我有一个后续问题,如果你不介意回答?在寻找修复它的方法时,我查看了使用对齐指南,但 HStacks 变得偏离中心。这归结于 SwiftUI 还是我必须更多地使用它们? 如果您不介意看一下,我已经更新了答案以显示 Horizo​​ntalAlignment 示例? 对齐参考线确实会移动视图,这就是轮廓不再对齐的原因。我没有看到一种在不移动轮廓的情况下获得对齐文本的明显方法。 哦,好的,谢谢您的解释和原始答案。

以上是关于SwiftUI在多个HStacks中对齐不同长度的文本的主要内容,如果未能解决你的问题,请参考以下文章

SwiftUI:底部对齐不同帧大小的文本和图像

在 ScrollView 中使用 GeometryReader 的 SwiftUI 布局

SwiftUI HStack 文本未对齐

Swift之深入解析SwiftUI布局如何自定义AlignmentGuides

ggplot:对齐多个刻面图-所有不同大小的刻面

如何使用 SwiftUI 将图像对齐到列表行的右上角?