[SwiftUI Mater] #14 UIViewControllerRepresentable

Woozoo·2023년 4월 3일
0

[SwiftUI Review]

목록 보기
29/41
post-custom-banner

UIViewController를 바꾸는 것도 이전에 했던 내용과 동일함
Representable 프로토콜을 채택해주면 된다.


sheet으로 segue를 해주면 뙇
방금 만든 UIViewController가 보입니다~

이제 UIViewController에 Label이 있다고 생각해봅시다


요렇게 프로퍼티 구멍 뚫어서 init할 때 값 넘겨줄 수도 있음!

struct BasicUIViewControllerRepresentable: UIViewControllerRepresentable {
    let labelText: String
    
    func makeUIViewController(context: Context) -> some UIViewController {
        return MyFirstViewController()
    }
    
    func updateUIViewController(_ uiViewController: UIViewControllerType, context: Context) {
    }    
}

class MyFirstViewController: UIViewController {
    var labelText: String = "Starting value"
    override func viewDidLoad() {
        super.viewDidLoad()
        
        view.backgroundColor = .blue
        
        let label = UILabel()
        label.text = labelText
        label.textColor = UIColor.white
        
        view.addSubview(label)
        label.frame = view.frame
    }
}

UIViewController를 사용하게 된다면 지금처럼 상속해서 사용하게 되는 경우가 많음
MyFirstViewController 라는 클래스를 만들어주고
view가 로드 될 때 지금까지 만든 label추가하는 코드, view의 백그라운드칼라 변경하는 코드를 구성해줬다


그리고 init할 때 받은 String으로 ViewController가 업데이트 될 수 있게 vc.labelText = labelText 로 만들어줌


이걸 사용하게 될 때는 UIKit에는 있고 SwiftUI에는 없는 것들이 필요하게 될 경우임


요렇게 UIImagePickerController같은 것들을 가져와서 사용함

이미지를 선택한 걸 가져오고 싶다고 해보자


Simple!
첫번째 스텝은 바인딩 해주면 됨

두번째는 Coordinator를 만들어줘야함!
uikit의 컨트롤러들이 SwiftUI의 인터페이스와 상호작용 하게 해주는 겨

makeUIVC에서 vc.delegate를 치면 어떤 Delegate이 필요한 지 알 수 있음


Coordinator클래스를 만들어주는데 한가지더 채택해줘야함

그리고 makeCoordinator()를 Coordinator가 반환되게 해주고
vc.delegate에 context.coordinator를 넘겨주면 된다

이렇게 하고 나면 Coordinator에선 delegate 메소드들을 사용할 수 있게 됨

struct UIImagePickerControllerRepresentable: UIViewControllerRepresentable {
    @Binding var image: UIImage?
    func makeUIViewController(context: Context) -> some UIImagePickerController {
        let vc = UIImagePickerController()
        vc.allowsEditing = false
        vc.delegate = context.coordinator
        return vc
    }
    // from SwiftUI to UIKit
    func updateUIViewController(_ uiViewController: UIViewControllerType, context: Context) {
        
    }
    
    // from UIKit to SwiftUI
    func makeCoordinator() -> Coordinator {
        return Coordinator(image: $image)
    }
    
    class Coordinator: NSObject ,UIImagePickerControllerDelegate, UINavigationControllerDelegate {
        @Binding var image: UIImage?
        
        init(image: Binding<UIImage?>) {
            self._image = image
        }
        func imagePickerController(_ picker: UIImagePickerController, didFinishPickingMediaWithInfo info: [UIImagePickerController.InfoKey : Any]) {
            guard let newImage = info[.originalImage] as? UIImage else { return }
            image = newImage
        }
    }
}

그러고 나서 didFinishi메소드에서 선택된 이미지를 전달해줘야하는데
@Binding으로 연결해서 UIImagePickerController까지 프로퍼티를 연결해줬음!

근데 지금 선택하고 나면 창이 안닫히는 현상이 있는데 showScreen도 바인딩해주면 좋을 거 같다

바인딩 바인딩~~~!~!

profile
우주형
post-custom-banner

0개의 댓글