如何在SwiftUI中忽略安全区域,以应用线性渐变和图像作为背景?

huangapple go评论60阅读模式
英文:

How to ignore safe area for a background with a linear gradient and image in swiftUI?

问题

我希望图像显示时不考虑安全区域,目前导致顶部出现白色空白,如此图所示:(https://i.stack.imgur.com/knRdm.png)。

我尝试通过添加偏移量来解决这个问题,但我注意到白色空白的高度在不同的模型上变化。

如何解决这个问题?

英文:

I have a VStack like this:

    var body: some View{
        VStack{
            //some view
        }
        .background(
            ZStack{
                LinearGradient(gradient: Gradient(
                    colors: [
                        .yellow_500,
                        .yellow_500,
                        .yellow_500,
                        .yellow_50
                    ]), startPoint: .top, endPoint: .bottom)
                .ignoresSafeArea(.container, edges: [.top])
                
                
                Image(R.image.home_bg_try.name)
                    .resizable()
                    .scaledToFill()
                    .frame(maxWidth: .infinity, maxHeight: .infinity)
                    .ignoresSafeArea(.container, edges: [.top])

            }
//                .offset(y: -20)
        )
    }

I want the image to be displayed without considering the safe area, which currently results in a white space appearing at the top, as shown in this image: (https://i.stack.imgur.com/knRdm.png).

I attempted to fix this issue by adding an offset, but I noticed that the height of the white space varies across different models.

How can I resolve this problem?

答案1

得分: 2

你当前的设置思路是正确的,但如果你想要完全忽略VStack的背景的安全区域,你应该在每个背景上应用.ignoresSafeArea()修饰符。

你看到的白色空白可能是因为VStack未填满整个屏幕。

尝试将.ignoresSafeArea()修饰符移到ZStack之外,并将其应用于整个VStack。以下是更新后的代码:

var body: some View {
    VStack{
        //某些视图
    }
    .background(
        ZStack {
            LinearGradient(gradient: Gradient(
                colors: [
                    .yellow_500,
                    .yellow_500,
                    .yellow_500,
                    .yellow_50
                ]), startPoint: .top, endPoint: .bottom)
                .resizable()
                .aspectRatio(contentMode: .fill)

            Image(R.image.home_bg_try.name)
                .resizable()
                .scaledToFill()
                .frame(maxWidth: .infinity, maxHeight: .infinity)
        }
    )
    .ignoresSafeArea()
}

通过使用.ignoresSafeArea(),你告诉SwiftUI在整个屏幕上包括状态栏和带边缘屏幕的iPhone模型下的主屏幕布局VStack及其背景。

此外,根据特定情况,你可能需要应用.edgesIgnoringSafeArea(.all)而不是.ignoresSafeArea()。例如,如果在将视图嵌入到另一个视图层次结构中时,你的视图在安全区域插入方面表现不佳,你可能会发现.edgesIgnoringSafeArea(.all)效果更好。但是,在SwiftUI 2.0及更高版本中,通常建议使用.ignoresSafeArea()

英文:

Your current setup has the right idea, but if you want to completely ignore the safe area for the VStack's background, you should apply the .ignoresSafeArea() modifier on each of the backgrounds.

The white space you are seeing might be a result of the VStack not filling up the whole screen.

Try moving .ignoresSafeArea() modifier outside of the ZStack, and apply it to the whole VStack. Here is the updated code:

var body: some View {
    VStack{
        //some view
    }
    .background(
        ZStack {
            LinearGradient(gradient: Gradient(
                colors: [
                    .yellow_500,
                    .yellow_500,
                    .yellow_500,
                    .yellow_50
                ]), startPoint: .top, endPoint: .bottom)
                .resizable()
                .aspectRatio(contentMode: .fill)

            Image(R.image.home_bg_try.name)
                .resizable()
                .scaledToFill()
                .frame(maxWidth: .infinity, maxHeight: .infinity)
        }
    )
    .ignoresSafeArea()
}

By using .ignoresSafeArea(), you instruct SwiftUI to layout the VStack and its background across the whole screen, including under the status bar and home indicator on iPhone models with edge-to-edge screens.

Additionally, you might want to apply .edgesIgnoringSafeArea(.all) instead of .ignoresSafeArea() in certain situations. For example, if your view doesn't play well with safe area insets when it's embedded in another view hierarchy, you might find .edgesIgnoringSafeArea(.all) works better. However, in SwiftUI 2.0 and later, .ignoresSafeArea() is generally recommended.

答案2

得分: 0

background 不会超出应用于它的 View 的尺寸。所以,如果您的 VStack 不覆盖安全区域,即使对其应用了 ignoresSafeArea 修饰符,也不会覆盖安全区域。

但是,您可以使用 ZStack,它会根据其最大的元素来调整自己的大小,在这种情况下,将忽略安全区域的背景。

var body: some View {
  ZStack {
    // 背景
    LinearGradient(gradient: Gradient(
      colors: [
        .yellow_500,
        .yellow_500,
        .yellow_500,
        .yellow_50
      ]), startPoint: .top, endPoint: .bottom)
    .ignoresSafeArea(.container, edges: [.top])

    // 内容
    VStack{
      //一些视图
    }
  }
}

// 背景视图
private var background: some View {
  ZStack {
    // 背景渐变
    LinearGradient(gradient: Gradient(
      colors: [
        .yellow_500,
        .yellow_500,
        .yellow_500,
        .yellow_50
      ]), startPoint: .top, endPoint: .bottom)
    .ignoresSafeArea(.container, edges: [.top])

    // 背景图像
    Image(R.image.home_bg_try.name)
      .resizable()
      .scaledToFill()
      .frame(maxWidth: .infinity, maxHeight: .infinity)
      .ignoresSafeArea(.container, edges: [.top])
  }
}

如果您有其他问题或需要进一步的翻译,请告诉我。

英文:

background never exceeds the size of the View it is applied to. So if your VStack doesn't cover the safe area, any background applied to it won't do so either, even if the background has an ignoresSafeArea modifier applied to it.

You can however, use a ZStack instead, which will size itself based on its largest element, which in this case will be your safe area ignoring background.

var body: some View {
  ZStack {
    background

    VStack{
      //some view
    }
  }
}

private var background: some View {
  ZStack {
    LinearGradient(gradient: Gradient(
      colors: [
        .yellow_500,
        .yellow_500,
        .yellow_500,
        .yellow_50
      ]), startPoint: .top, endPoint: .bottom)
    .ignoresSafeArea(.container, edges: [.top])

    Image(R.image.home_bg_try.name)
      .resizable()
      .scaledToFill()
      .frame(maxWidth: .infinity, maxHeight: .infinity)
      .ignoresSafeArea(.container, edges: [.top])
  }
}

huangapple
  • 本文由 发表于 2023年6月1日 23:15:11
  • 转载请务必保留本文链接:https://go.coder-hub.com/76383390.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定