[SwiftUI] 5. View Layout: 콘텐츠 계층화

Sean·2023년 5월 3일
0

SwiftUI_튜토리얼

목록 보기
5/11

참고 자료: SwiftUI 튜토리얼 공식문서

이제 막 SwiftUI를 배워보는 한 사람으로서, 코드 작성하고 내가 이해 한 대로 작성할것이다.

이 글의 내용은 위에 있는 참고자료의 공식문서를 번역하여 조금 더 내가 느끼기에 자연스럽게 만들어서 작성하는것이다.

누군가에게 알려주기보다 자신이 정리를 하면서 다시 문서를 보고 어버버거리지 않게 다시 참고하기 위함이기에 해당 문서를 읽는 사람은 swift에 대해서 어느 정도 안다는 가정하에 글을 작성할것이다

시작

기본 컨텐츠에 맞게 view를 오버레이 또는 백그라운드에 정의하여 레이아웃을 조정한다.
레이어 컨텐츠 디자인은 종종 일부 컨텐츠가 다른 컨텐츠 범위내에 머무르게 지정하거나 해당 컨텐츠 주위에 특정 여백을 유지하도록 지정한다.
이러한 view간의 관계를 오버레이 및 백그라운드 수정자를 사용해 정의할 수 있다.

예를 들어, 텍스트 뒤에 대비를 주는 그래픽을 포함하는 디자인을 만들 경우, 해당 그래픽이 텍스트 업데이트에 따라 크기와 위치를 조정할 수 있도록 레이아웃을 정의할 수 있다.
또한, 다른 view의 백그라운드 또는 오버레이에 텍스트를 정의함으로써 해당 view의 너비에 맞게 텍스트 줄 바꿈할 수 있다.

분석

1. 오버레이 정의 (Define an overlay)

Method: overlay()
Method: background()

안봐도 이해할 수 있게 글은 작성할 예정이지만 그래도 코드를 봐야 따라 작성이 가능하다.
샘플코드

CaptionedPhoto.swift

import SwiftUI

struct CaptionedPhoto: View {
    let assetName: String
    let captionText: String
    var body: some View {
        Image(assetName)
            .resizable()
            .scaledToFit()
            .overlay(alignment: .bottom) {
                Caption(text: captionText)
            }
            .clipShape(RoundedRectangle(cornerRadius: 10.0, style: .continuous))
            .padding()
    }
}

struct Caption: View {
    let text: String
    var body: some View {
        Text(text)
            .padding()
            .background(Color("TextContrast").opacity(0.75),
                        in: RoundedRectangle(cornerRadius: 10.0, style: .continuous))
            .padding()
    }
}

Preview

struct CaptionedPhoto_Previews: PreviewProvider {
    static let landscapeName = "Landscape.jpeg"
    static let landscapeCaption = "This photo is wider than it is tall."
    static let portraitName = "Portrait.jpeg"
    static let portraitCaption = "This photo is taller than it is wide."
    static var previews: some View {
        CaptionedPhoto(assetName: portraitName,
                       captionText: portraitCaption)
        CaptionedPhoto(assetName: landscapeName,
                       captionText: landscapeCaption)
        .preferredColorScheme(.dark)
        CaptionedPhoto(assetName: landscapeName,
                       captionText: landscapeCaption)
        .preferredColorScheme(.light)
    }
}

z축에 컨텐츠를 정렬할때 ZStack, 오버레이 또는 백그라운드와 같은 수정자를 사용할 수 있다.
ZStack은 스택 내 다른 뷰들의 크기는 고려않고 사용 가능 공간에 따라 각 뷰의 크기를 결정한다.
따라서 어떤 컨텐츠의 크기가 다른 컨텐츠의 크기에 의존해야 하는 경우 이 보조 컨텐츠를 오버레이나 백그라운드 중 하나로 감싸서 정의 한다.

해당 예시는 하단부에 텍스트 블록이 있는 사진을 보여준다. 텍스트가 사진의 그 부분을 완전히 가리지 않으면서도 텍스트의 가독성을 높이기 위해 텍스트 위에 투명한 배경이 있다.
사진 너비에 맞게 텍스트가 줄바꿈 되며 텍스트 주위의 배경은 텍스트를 감싸는 크기로 조정이 된다.
해당 view는 이미지를 배열하고 이미지의 오버레이에서 Caption view에 텍스트를 제공한다.

기본적으로 Image는 이미지를 원래 크기로 표시를 한다. 하지만 resizavle() 및 scaledToFit()을 사용하면 이미지를 사용가능한 공간에 맞게 조정한다.

body의 상단에 있는 Image가 최상위 view 이기에 Imgae가 view의 크기를 결정한다.

overlay()를 사용하여 캡션을 정의하면, 캡션이 이미지 앞에 배치되도록 지정된다.
기본 view의 크기가 view를 수정하는 overlay의 크기를 제한한다.
overlay의 정렬을 지정하면 내부의 컨텐츠가 view에 정렬된다.

보여지는 이미지의 크기나 위치를 변경하지 않고 RoundedRectangle를 사용해 이미지의 모서리를 둥글게 만든다.
Struct: RoundedRectangle

2. 배경 정의 (Define a backgroud)

CaptionPhoto의 오버레이에는 Caption view가 포함되어있다.
이 view는 텍스트 뒤에 있는 컨텐츠를 부분적으로 가려 텍스트에 더 높은 대비를 제공한다.

샘플 코드 : Caption 구조체 참고

padding()을 주어 단어와 그 아래 대조되는 배경 가장자리 사이에 약간의 공간을 추가한다.

패딩을 오버레이나 백그라운드오 결합할 때는 신중하게 선택해야 한다. 오버레이 또는 백그라운드를 수정하기 전에 view를 패딩하면 시스템은 패딩된 기본 view 의 크기를 사용하여 보조 view의 배치를 계산한다.
오버레이 또는 백그라운드 다음에 패딩을 적용하면 두 레이어를 모두 포함 하는 view 주위에 약간의 공간을 둔다.

백그라운드 수정자는 수정하는 뷰의 크기를 기반으로 컨텐츠의 크기를 조정하는 오버레이 수정자와 유사하다
그러나 백그라운드는 수정하는 view의 뒤에 컨텐츠를 배치하게 되어 view의 앞쪽이 아닌 뒷쪽에 설정이 된다.

참고자료

Struct: RoundedRectangle

Method: overlay()
Method: background()

기타

당연 틀린 부분 지적은 감사하나 비난은 정중하게 사양하겠다.

수정자? 제어자?라고 번역이 되어지는 modifier를 어떻게 해야 조금더 쓰는데 부드러우면서 읽을때도 부드러운 단어로 의역을 하면 좋을지 도저히 모르겠다.

profile
"잘 할 수 있을까?"를 고민하기보단 재밌어 보이는건 일단 하고, 잘하기 위해 그냥 계속합니다.

0개의 댓글