UIImagePickerController

POPO 표지 선택 타입 중 하나, 사용자가 12개의 사진을 선택해서 올리는 뷰다.
사용자의 갤러리에 있는 사진을 업로드하고, 서버로 보내기 전까지 개발할 예정!
UIImagePickerController 만들기
var photoPicker = UIImagePickerController()
UIImagePickerController를 선언해준다.
권한 위임하기
private func assignDelegate() {
imagePicker.delegate = self
}
delegate를 위임해준다.
extension 만들기

요런 오류가 뜨는걸로 봐서,
UIImagePickerControllerDelegate, UINavigationControllerDelegate 둘을 상속받는
extensions을 만들어줘야 하는 것 같다.
왜 UINavigationControllerDelegate도 상속받아야 하는지 궁금해서 찾아봤더니,
UIImagePickerControllerDelegate의 delegate 속성은 UIImagePickerControllerDelegate와 UINavigationControllerDelegate 프로토콜을 모두 구현하는 객체로 정의되어있다.
(위에서 해준 picker.delegate = self) self를 picker.delegate에 할당하려면 self는 UINavigationControllerDelegate 타입이어야 한다.
지금, picker의 델리게이트를 UINavigationControllerDelegate에 위임해준 것인데, 대리자는 사용자가 이미지나 동영상을 선택하거나 picker화면을 종료할 때, 알림을 받는다.
라고 한다. 출처
extension CoverUserPhotoViewController: UIImagePickerControllerDelegate, UINavigationControllerDelegate {
// didFinishPickingMediaWithInfo
func imagePickerController(_ picker: UIImagePickerController, didFinishPickingMediaWithInfo info: [UIImagePickerController.InfoKey : Any]) {
}
}
didFinishPickingMediaWithInfo 함수도 선언해준다.
docs 를 보면, 유저가 사진이나 동영상을 선택했음을 delegate에게 알려준다는 함수다.
이따 여기서 서버에 보낼 데이터에 이미지도 저장하고, 표지 이미지뷰의 이미지도 바꿔줄 것이다.
photoLibrary 띄우기
이제 사용자가 각 + 뷰를 눌렀을 때, 각각의 표지 뷰에 들어갈 사진을 고를
photoLibrary(갤러리)가 띄워져야 한다.
각각의 + 이미지 뷰에 UITapGestureRecognizer를 달아준다.
private func initTapGesterRecognizer() {
for (index, coverImageView) in coverImageViews.enumerated() {
let coverTapRecognizer = UITapGestureRecognizer(target: self, action: #selector(touchCover(_:)))
coverTapRecognizer.numberOfTapsRequired = 1
coverImageView.tag = index
coverImageView.isUserInteractionEnabled = true
coverImageView.addGestureRecognizer(coverTapRecognizer)
}
}
각 이미지뷰가 몇 번째 커버 이미지인지 가지고 있어야 해서,
TapGestureRecognizer를 붙여줄 때 coverImageView의 idx를 coverImageView의 tag로 붙여줬다.
이는 다음에 handler 함수에서 sender.view가 imageView가 되므로 sender.view.tag로 참조할 수 있게 된다.
handler 함수도 만들어준다.
// MARK: - @IBAction Functions
@objc func touchCover(_ sender: UITapGestureRecognizer) {
imagePicker.sourceType = .photoLibrary
guard let senderTag = sender.view?.tag else { return }
currentPickerIndex = senderTag
present(imagePicker, animated: true, completion: nil)
}
이 부분이 UIImagePickerController를 띄우는 부분인데,
띄울 때 트리거된 UITapGestureRecognizer의 tag값을 현재 피커의 인덱스값을 저장해놓는 전역변수
currentPickerIndex에 넣어준다.
// MARK: - UIImagePickerControllerDelegate & UINavigationControllerDelegate
extension CoverUserPhotoViewController: UIImagePickerControllerDelegate, UINavigationControllerDelegate {
// didFinishPickingMediaWithInfo
func imagePickerController(_ picker: UIImagePickerController, didFinishPickingMediaWithInfo info: [UIImagePickerController.InfoKey : Any]) {
// 선택한 이미지 커버 이미지뷰의 이미지로 변경
if let image = info[UIImagePickerController.InfoKey.originalImage] as? UIImage {
coverImageViews[currentPickerIndex].image = image
}
dismiss(animated: true, completion: nil)
}
}
extension에 구현해둔 didFinishPickingMediaWithInfo 함수의 내용도 채워준다.
이 때, info는 딕셔너리인데,
info를 print해 보니까
[__C.UIImagePickerControllerInfoKey(_rawValue: UIImagePickerControllerReferenceURL): assets-library://asset/asset.JPG?id=106E99A1-4F6A-45A2-B320-B0AD4A8E8473&ext=JPG, __C.UIImagePickerControllerInfoKey(_rawValue: UIImagePickerControllerMediaType): public.image, __C.UIImagePickerControllerInfoKey(_rawValue: UIImagePickerControllerImageURL): file:///Users/choyi/Library/Developer/CoreSimulator/Devices/61DF3D8E-5E65-422A-B845-BC6E740AFC91/data/Containers/Data/Application/4F57E11F-5AEE-44D5-B8DB-A134D9DDF8CF/tmp/FDAA3411-9412-4539-844A-3699C54794A5.jpeg, __C.UIImagePickerControllerInfoKey(_rawValue: UIImagePickerControllerOriginalImage): <UIImage:0x600003c1c000 anonymous {4288, 2848}>]
요런 로그가 찍힌다.

키값으로는 요런 것들이 있다고 한다!
info.plist 에서 권한 요청하기

이렇게 두 개 추가해준다.

잘 된다.
extension CoverUserPhotoViewController: UIImagePickerControllerDelegate, UINavigationControllerDelegate {
// didFinishPickingMediaWithInfo
func imagePickerController(_ picker: UIImagePickerController, didFinishPickingMediaWithInfo info: [UIImagePickerController.InfoKey: Any]) {
// 선택한 이미지 커버 이미지뷰의 이미지로 변경
if let image = info[UIImagePickerController.InfoKey.originalImage] as? UIImage {
coverImageViews[currentPickerIndex].image = image
selectedCoverImages[currentPickerIndex] = image
}
dismiss(animated: true, completion: nil)
}
}
didFinishPickingMediaWithInfo 함수에 나중에 서버로 이미지 배열을 보내기 위해
selectedCoverImages[currentPickerIndex] = image 추가하면 끝!