skip to Main Content

I am trying to offset an image to make a nice profile view but the image is cut-off as shown in the image below:

enter image description here

and below is the code:


 NavigationStack {
            ScrollView(.vertical) {
                Section() {
                    VStack() {
                        Image("dflt_profile_img")
                            .resizable()
                            .frame(width: /*@START_MENU_TOKEN@*/100/*@END_MENU_TOKEN@*/, height: 100)
                            .clipShape(RoundedRectangle(cornerRadius: /*@START_MENU_TOKEN@*/25.0/*@END_MENU_TOKEN@*/))
                            .padding(12)
                            .offset(y: -50.0)
                    }
                    .frame(maxWidth: /*@START_MENU_TOKEN@*/.infinity/*@END_MENU_TOKEN@*/)
                    .background(Color.cOrange.opacity(0.25))
                    .clipShape(RoundedRectangle(cornerRadius: 25.0))
                    .padding([.leading, .trailing], 24)
                    .padding(.top, 50)

                    
                }
                
            }

Any idea how to have the profile image not cut-off but still position on top of the stack aligned in the middle of the image.

2

Answers


  1. The image is being clipped because you applied .clipShape on the VStack. As its name suggests, clipShape clips the contents of the view.

    You can use background(_:in:) to apply a background to only a specific region of the view, as determined by a Shape.

    VStack() {
        Image("my_image")
            .resizable()
            .frame(width: 100, height: 100)
            .clipShape(RoundedRectangle(cornerRadius: 25.0))
            .padding(12)
            .offset(y: -50.0)
    }
    .frame(maxWidth: .infinity)
    // here!
    .background(.orange.opacity(0.25), in: RoundedRectangle(cornerRadius: 25.0))
    .padding(.horizontal, 24)
    .padding(.top, 50)
    

    enter image description here

    Login or Signup to reply.
  2. I would suggest using a ZStack with alignment: .top as container for the VStack and the image. This way, you just need to apply top padding to the VStack (which you were doing already), the offset on the image can be removed.

    Section() {
        ZStack(alignment: .top) {
            VStack {
                // ...main content
            }
            .frame(maxWidth: .infinity, minHeight: 100)
            .background(Color.orange.opacity(0.25))
            .clipShape(RoundedRectangle(cornerRadius: 25.0))
            .padding([.leading, .trailing], 24)
            .padding(.top, 50)
    
            Image("dflt_profile_img")
                .resizable()
                .frame(width: 100, height: 100)
                .clipShape(RoundedRectangle(cornerRadius: 25.0))
                .padding(12)
        }
    }
    

    Screenshot

    Login or Signup to reply.
Please signup or login to give your own answer.
Back To Top
Search