iOS/Xcode, UI

Notification(1) - NotificationCenter 사용하기

KemiKIM 2023. 1. 22. 19:46

(Macbook Air M1 8-256 Monterey 12.6.2 Xcode 13.4)

 

 

Why?

 

 

매주 스터디에서 주제를 정해서 그 주제에 대한 발표를 진행하고 있는데,

이번에 ' Notification '을 맡게 되었습니다.

그래서 이번 포스팅에서는 Notification 사용에 대해 알아보겠습니다.

 

 

 

크게

 

 (1) Notification

 (2) NotificationCenter

 (3) 사용법

 (4) 어떤 상황에서 사용할까?

 

순으로 작성되었습니다.

 

 

 


 

 

(1) Notification

 

보통 Noti를 사용한다.라고 이야기를 하면

크게 2가지 의미로 받아들일 수 있을 것 같습니다.

 

 

1. Event를 전달한다.

2. 사용자 알림 push를 전달 remote

 

 

이 중 Event를 전달하는 내용을 포스팅해보려고 합니다.

 

 

 

 

공식문서의 Notification의 정의를 보면,

 NotificationCenter를 통해서 등록된 모든 옵저버에게

브로드캐스트 되는 정보를 위한 container이며, 구조체라고 나와있습니다.

 

 

이해하기 편하게 해석해본다면,

Center를 통해 / 해당되는 이름을 가진 사람에게 / 정보를 줄 내용을 담는 함수이다.

 

다시 풀어보면,

 

어떤 Center를 통해 전달할 수 있으며,

 해당되는 이름을 가진 사람에게,

 그 이름에 맞는 정보를 담는 하나의 바구니

 

라고 생각하시면 될 것 같습니다.

 

보통 방송국에 비유해서 많이 설명이 되곤 하는데,

개인에 맞게끔 이해하시면 될 것 같습니다 :)

 

 

 

 

Notification이라는 구조체는 3가지 변수를 가지고 있습니다.

이 변수의 의미를 익혀두고 사용하시면,

조금 더 편리합니다.

 

 

var name: Notification.name

 알림을 식별하는 '태그'

 

 

 var object: Any?

 발송자가 옵저버에게 보내려고 하는 객체를 의미

주로 발송자 객체를 전달하는데 쓰입니다.

 

 

 var userInfo: [AnyHashable : Any]?

 Notification과 관련된 값 또는 객체의 저장소.

 

 

 

이 중

분별을 위해 .Name을 가장 많이 사용되며,

의미는 위에 변수 name과 동일하다고 보시면 되겠습니다.

 

 

 

 

 

보통 Notification을 사용하려고 code에 치면, 하단에 이렇게 4가지가 나옵니다.

 

3번 NotificationEX의 경우 module이기 때문에 제외하고,

(module: 코드를 배포하는 단일 단위)

일반적으로 Notification, NotificationCenter를 많이 사용되며,

NotificationQueue의 경우 비동기적으로 처리할 때 사용됩니다.

 

 

추가적으로 push 알림을 remote하고 싶다면,

UNUserNotificationCenter을 사용하시면 됩니다.

 

 

 

 

 


 

 

 

 

(2) NotificationCenter

 

 

공식문서의 NotificationCenter 정의를 확인해보면,

등록된 옵저버에게 정보를 알릴 수 있는

'알림 발송 메커니즘'

 이라고 하는데요.

 

 

 이 메커니즘을 통해

Event를 주고 받는 것이라고

생각하시면 될 것 같습니다.

 

 

 

 NotificationCenter에는 여러 method가 있는데,

그 중 가장 많이 사용되는 것을 살펴보면

 post, addObserver, removeObserver 3가지가 있으며,

내부 method에 접근하려면 (dot을 통한)

반드시 default를 통해 접근해야 합니다.

 

 

 

 

이유는 

default가 notificationcenter을 사용하기 위한

필수 기본값으로 설정되어 있기 때문입니다.

 

 

 

 이렇게 접근해서 나오는 3가지 method에 대해 살펴보자면,

 

 

 

 post

'발송'의 의미인 method입니다.

 느낌을 '지시할게'로 가져가시면 편할 것 같습니다.

 

 

 addObserver

'관찰자 지정'의 의미인 method입니다.

 느낌을 '지시해줘'로 가져가시면 편합니다.

 

 

 removeObserver

'관찰자 제거'의 의미인 method입니다.

 우리가 view를 만들고 없앨 때, 메모리에서 해제하는 것까지 고려를 하죠.

 Notification에서도 마찬가지로

동일한 역할이라고 생각하시면 편할 것 같습니다.

 

 

 

 

 

 

 위 3가지 Method를 기반으로 사용방법을 알아보겠습니다.

 

 

 

 


 

 

 

(3) 사용법

 

 

 준비한 내용은 VC 2개이며,

 noti를 통해

VC2 버튼을 누르면, VC1의 backgroundColor를 바꿔주는

아주 간단한 내용을 구현해보겠습니다.

완성내용

 

 

 

[1]

 

 

 먼저 보내는 VC(여기에선 VC2)에서 Name을 먼저 설정해줍니다.

 

여기서 상수를 static으로 선언한 이유는

 해당 property가 instance보다는 type 자체와 연관되어 있기 때문입니다.

 즉, 단 하나만 존재하고 바로 처리하고 끝내기 위함인데

 

속성으로 선언해주는 것 자체가 '메모리에 올라가는 것'이기 때문에

메모리에 올리지 않고, 처리하기 위함이기도 합니다.

 

 

 

 

[2]

 보내는 VC에서 받을 VC로 가는 '경로'에 post를 작성해줍니다.

 

(여기서 경로는 button의 action부분입니다.)

 

 

 

 

 

[3]

 받을 VC에서 Observer를 작성합니다.

 받을 VC에서 사용할 함수를 작성해 selector에 등록합니다.

 

 object를 nil로 설정해두면 name에서 설정한 Notification은 어떤 객체가 보내더라도 받을 수 있습니다.

 

 

 

 

[ + ]

잠깐, 구현은 끝났는데, 사용하지 않은 method가 있습니다.

removeObserver는 어디서 사용하는걸까요?

 

받을 VC에서 Observer를 작성하여 등록했을 때

Observer는 메모리에 올라가있는 상태입니다.

 

 

 

그럼 다른 View로 가기 전에, (즉, 사용을 다 했다면)

당연히 메모리에서 Observer를 내려줘야합니다.

 

그 역할을 removeObserver가 하는 것인데,

반드시 removeObserver를 등록할 필요는 없습니다.

 

removeObserver Discussion

 

공식문서에 나온,

removeObserver Discussion 두번째 문단을 보시면,

 

"

앱이 iOS 9.0 이상 또는 macOS 10.11 이상을 대상으로 하고 

addObserver(_:selector:name:object:)를 사용하여 

관찰자를 생성한 경우 

관찰자를 등록 해제할 필요가 없습니다. 

 

관찰자를 잊었거나 제거할 수 없는 경우 

시스템은 다음에 게시했을 때 정리합니다.

"

 

라고 나와있습니다.

 

 

2022년 기준으로,

iOS 9.0 이하를 만들고 있는 App은

사실상 없다고 봐도 무방하겠죠.

 

 

 

 

사실 view가 사라지면서 deinit되면

해당 옵저버도 같이 해제되기도 하고,

 

 google검색결과 옵저버 해제에 대한 내용이 많이 없는 것을 보면,

 이런 내용을 기반으로 하고 있기 때문에

없는거라고 추측됩니다.

 

 

 

 만약 너무 불안해서

반드시 메모리에서 내리겠다고 생각하신다면,

 viewDidLoad - deinit

 viewWillAppear - viewWillDisappear or viewDidDisapper를

 조합해 등록 및 해제 method를 사용하시면 됩니다.

 

 

 

 이 모든과정은 동기적으로 발생됩니다.

 

 

 


 

 

 

(4) 어떤 상황에서 사용할까?

 

 

 

스위프트는 delegate pattern을 중점으로 밀고 있는만큼

그 빈도가 비교적 낮을 것으로 예상하지만,

그래도 사용한다면

 

 (1) 1:N로 data를 전달해야하는 상황

 (2) 알 수 없는 이유로 delegate가 먹히지 않는 상황.

(3) 그 외 본인이 편한대로

 

라고 생각해볼 수 있겠습니다.

 

 

 

 

 

 

 


 

 

 

 

 

이렇게 Notification과 NotificationCenter에 대해 공부해보았습니다.

 

다음에 시간이 된다면,

이번에 다루지 못한 NotificationQueue와, UNUserNotificationCenter에 대해 공부해봐야겠네요. :)

 

 

 

 

오류가 있거나, 피드백이 있다면 언제든지 댓글로 알려주세요!

감사합니다 :)

 

 

 

 

 

- 참고자료: https://developer.apple.com