종류: SwiftUI

참고영상

Demystify SwiftUI - WWDC21 - Videos - Apple Developer

SwiftUI

  • 선언형 프레임워크이지만 예상하지 못한 결과가 나온 적이 있음
  • swiftUI가 가지고 있는 세가지
    • identity
      • element가 같은지 다른지 판단
    • lifetime
      • view의 데이터를 트래킹하는 시간
    • dependencies
      • inhterface가 언제 업데이트되는지

    → 위 세가지로 what needs to change, how and when dynamic user interface를 그릴 수 있게 됨

Identity

ex) 탭해서 good, bad를 바꾸는 앱

스크린샷 2024-03-13 오후 9.47.18.png

  • 같은 뷰라면 슬라이드를 해야하고 다른 뷰라면 fade in, out 처럼 움직여야 함

view는 같은 identity를 사용한다 → 같은 element를 가져야 함

다른 identity를 사용한다 → 다른 element를 가져야 한다

스크린샷 2024-03-13 오후 9.49.04.png

스크린샷 2024-03-13 오후 9.49.15.png

identity의 종류

  • explicit identity: using custom or data-driven identifiers.
    • assign name or identity
    • 강력하지만 모든 이름들을 트래킹해야 함
  • structural identity: distinguishing views by their type and position in the view hierarchy.

Explicit identity

  • pointer identity도 포함되긴 하지만 swiftUI는 사용하지 않고 uiKit만 사용함

Pointer identity

스크린샷 2024-03-13 오후 9.54.37.png

스크린샷 2024-03-13 오후 9.56.19.png

  • swiftUI는 value type이니까 pointer identity를 사용하지 않는 것!

스크린샷 2024-03-13 오후 9.55.08.png

→ 따라서 SwiftUi는 다른 걸로 id를 사용(/assets/2024-03-13-Demystify-SwiftUI/id)

스크린샷 2024-03-13 오후 9.57.11.png

  • 혹은 .id modifier를 통해서 id를 지정할 수도 있어 스크롤뷰에서 지정된 뷰로 올라가도록 할 수 있음

Structual identity

view 문 안에 있는 if가 바로 예시

스크린샷 2024-03-13 오후 9.59.32.png

스크린샷 2024-03-13 오후 10.00.49.png

view 프로토콜은 암시적으로 viewBuilder를 래핍하며 이를 통해 단일 제너릭 뷰를 구성함!

→ 따라서 서로 다른 뷰를 나타내는 고유한 식별자를 가지고 있기 때문에 뷰가 전환됨

그렇다면 같은 뷰 전환으로 표현하고 싶다면??

스크린샷 2024-03-13 오후 10.03.34.png

  • 위의 방식이 swiftUI가 추천하는 방식!

AnyView

스크린샷 2024-03-13 오후 10.04.36.png

  • 위에처럼 some View를 리턴할 때 타입이 같아야 하니까 anyView로 랩핑할 수 있음
  • 하지만 이럴 경우 conditional view임을 인지하지 못하여 anyView를 type erasing wrapper type이라고도 부름!

→ 좀 더 스유답게 바꿔보자!

스크린샷 2024-03-13 오후 10.09.06.png

  • AnyView와 return을 없앴고 @viewBuilder를 추가, swift문으로 변경
  • viewBuilder를 통해서 뷰를 다른 뷰를 리턴해도 에러 없어질 수 있게 됨

Note: AnyView가 너무 많으면 이해하기 어렵게 되고 compile time에 에러가 발생할 수 있기 때문에 남용하면 안됨


LifeTime

스크린샷 2024-03-13 오후 10.11.31.png

  • identity는 element가 시간에 따라 value가 달라질 수 있음

Note: view value ≠ view identity임을 유의

  • view의 lifetime은 duration of the identity를 의미함
  • @State, @StateObject가 바로 view의 identity와 함꼐 가는 stoerage라고 보면 됨

스크린샷 2024-03-13 오후 10.15.27.png

스크린샷 2024-03-13 오후 10.17.03.png

  • true로 가다가 false로 가면 따로 storage를 만들고 true일 때의 storage는 destory가 됨

Note: state(/assets/2024-03-13-Demystify-SwiftUI/identity) lifetime = view lifetime

ForEach

  • 보여줄려는 타입이 identifiable을 만족해야 워닝 없이 stable identity for you data가 가능
  • id를 .self 혹은 매번 UUID(/assets/2024-03-13-Demystify-SwiftUI/)를 리턴하는 변수를 id로 사용하면 not stable이므로 추가, 삭제 되면 모두 다시 그리게 됨 유의할 것
  • 또한 id를 unique하지 않는 변수로 정하게 되면 일부가 가려지는 경우가 있기에 유의할 것

Dependenicies

  • view의 input
  • input이 달라지면 body를 다시 그려야 함
  • action은 view의 dependecies를 바꾸게 하는 trigger

    스크린샷 2024-03-13 오후 10.24.24.png

  • dependency graph를 통해 어떤 뷰가 어떻게 영향받는지 알 수 있음
  • identity는 graph의 backbone

스크린샷 2024-03-13 오후 10.28.01.png


정리

  • 처음 코드처럼 그리면 같은 뷰이지만 다른 identity를 가지기 때문에 뒤의 코드처럼 뷰를 그려야 같은 identity를 가지게 됨

스크린샷 2024-03-13 오후 10.34.38.png

스크린샷 2024-03-13 오후 10.34.43.png

스크린샷 2024-03-13 오후 10.32.45.png

스크린샷 2024-03-13 오후 10.36.01.png