|
| 1 | +// |
| 2 | +// WritingReviewModalViewController.swift |
| 3 | +// EATSSU-DEV |
| 4 | +// |
| 5 | +// Created by 최지우 on 2/2/25. |
| 6 | +// |
| 7 | + |
| 8 | +import UIKit |
| 9 | + |
| 10 | +import EATSSUDesign |
| 11 | + |
| 12 | +final class WritingReviewModalViewController: BaseViewController { |
| 13 | + |
| 14 | + // MARK: - Properties |
| 15 | + |
| 16 | + // View Properties |
| 17 | +// private let writingReviewModalView = WritingReviewModalView() |
| 18 | + |
| 19 | + private var userPickedImage: UIImage? |
| 20 | + |
| 21 | + // MARK: - UI Components |
| 22 | + |
| 23 | + private var rateView = RateView() |
| 24 | + private let imagePickerController = UIImagePickerController() |
| 25 | + |
| 26 | + private var titleLabel: UILabel = { |
| 27 | + let label = UILabel() |
| 28 | + label.text = "리뷰 남기기" |
| 29 | + label.font = EATSSUDesignFontFamily.Pretendard.bold.font(size: 16) |
| 30 | + return label |
| 31 | + }() |
| 32 | + |
| 33 | + private var questionLabel: UILabel = { |
| 34 | + let label = UILabel() |
| 35 | + label.text = "오늘 식사는 어떠셨나요" |
| 36 | + label.font = EATSSUDesignFontFamily.Pretendard.bold.font(size: 16) |
| 37 | + return label |
| 38 | + }() |
| 39 | + |
| 40 | + private let userReviewTextView: UITextView = { |
| 41 | + let textView = UITextView() |
| 42 | + textView.font = EATSSUDesignFontFamily.Pretendard.medium.font(size: 14) |
| 43 | + textView.layer.cornerRadius = 12.adjusted |
| 44 | + textView.backgroundColor = EATSSUDesignAsset.Color.GrayScale.gray100.color |
| 45 | + textView.layer.borderWidth = 1.adjusted |
| 46 | + textView.layer.borderColor = EATSSUDesignAsset.Color.GrayScale.gray200.color.cgColor |
| 47 | + textView.textContainerInset = UIEdgeInsets(top: 12.0.adjusted, |
| 48 | + left: 12.0.adjusted, |
| 49 | + bottom: 12.0.adjusted, |
| 50 | + right: 12.0.adjusted) |
| 51 | + textView.text = "메뉴에 대한 상세한 리뷰를 작성해주세요" |
| 52 | + textView.textColor = EATSSUDesignAsset.Color.GrayScale.gray400.color |
| 53 | + return textView |
| 54 | + }() |
| 55 | + |
| 56 | + private lazy var userReviewImageView: UIImageView = { |
| 57 | + let imageView = UIImageView() |
| 58 | + imageView.layer.cornerRadius = 10 |
| 59 | + imageView.clipsToBounds = true |
| 60 | + |
| 61 | + let tapGesture = UITapGestureRecognizer(target: self, action: #selector(didTappedimageView)) |
| 62 | + imageView.isUserInteractionEnabled = true |
| 63 | + imageView.addGestureRecognizer(tapGesture) |
| 64 | + return imageView |
| 65 | + }() |
| 66 | + |
| 67 | + private lazy var selectImageButton: UIButton = { |
| 68 | + let button = UIButton() |
| 69 | + button.setImage(EATSSUDesignAsset.Images.photoUpload.image, for: .normal) |
| 70 | + button.addTarget(self, action: #selector(didSelectedImage), for: .touchUpInside) |
| 71 | + return button |
| 72 | + }() |
| 73 | + |
| 74 | + private let deleteMethodLabel: UILabel = { |
| 75 | + let label = UILabel() |
| 76 | + label.text = "이미지 클릭 시, 삭제됩니다" |
| 77 | + label.font = .caption3 |
| 78 | + label.textColor = EATSSUDesignAsset.Color.GrayScale.gray500.color |
| 79 | + return label |
| 80 | + }() |
| 81 | + |
| 82 | + private let maximumWordLabel: UILabel = { |
| 83 | + let label = UILabel() |
| 84 | + label.text = "0 / 300" |
| 85 | + label.font = .caption2 |
| 86 | + label.textColor = EATSSUDesignAsset.Color.GrayScale.gray600.color |
| 87 | + return label |
| 88 | + }() |
| 89 | + |
| 90 | + private var nextButton: UIButton = { |
| 91 | + var config = UIButton.Configuration.plain() |
| 92 | + var container = AttributeContainer() |
| 93 | + container.font = EATSSUDesignFontFamily.Pretendard.bold.font(size: 16) |
| 94 | + container.foregroundColor = EATSSUDesignAsset.Color.Main.primary.color |
| 95 | + config.attributedTitle = AttributedString("완료하기", attributes: container) |
| 96 | + config.contentInsets = .init(top: 0, leading: 0, bottom: 0, trailing: 0) |
| 97 | + let button = UIButton(configuration: config) |
| 98 | + return button |
| 99 | + }() |
| 100 | + |
| 101 | + override func viewDidLoad() { |
| 102 | + super.viewDidLoad() |
| 103 | + setDelegate() |
| 104 | + } |
| 105 | + |
| 106 | + override func viewWillAppear(_: Bool) { |
| 107 | + addKeyboardNotifications() |
| 108 | + } |
| 109 | + |
| 110 | + override func viewWillDisappear(_: Bool) { |
| 111 | + removeKeyboardNotifications() |
| 112 | + } |
| 113 | + |
| 114 | + // MARK: - Functions |
| 115 | + |
| 116 | + override func configureUI() { |
| 117 | + dismissKeyboard() |
| 118 | + view.addSubviews( |
| 119 | + titleLabel, |
| 120 | + nextButton, |
| 121 | + questionLabel, |
| 122 | + rateView, |
| 123 | + maximumWordLabel, |
| 124 | + selectImageButton, |
| 125 | + userReviewImageView, |
| 126 | + userReviewTextView, |
| 127 | + deleteMethodLabel) |
| 128 | + } |
| 129 | + |
| 130 | + override func setLayout() { |
| 131 | + titleLabel.snp.makeConstraints { make in |
| 132 | + make.top.equalToSuperview().inset(20) |
| 133 | + make.centerX.equalToSuperview() |
| 134 | + } |
| 135 | + |
| 136 | + nextButton.snp.makeConstraints { make in |
| 137 | + make.top.equalTo(titleLabel) |
| 138 | + make.trailing.equalToSuperview().inset(30) |
| 139 | + } |
| 140 | + |
| 141 | + questionLabel.snp.makeConstraints { make in |
| 142 | + make.top.equalTo(titleLabel.snp.bottom).offset(30) |
| 143 | + make.centerX.equalToSuperview() |
| 144 | + } |
| 145 | + |
| 146 | + rateView.snp.makeConstraints { make in |
| 147 | + make.top.equalTo(questionLabel.snp.bottom).offset(35) |
| 148 | + make.centerX.equalToSuperview() |
| 149 | + make.height.equalTo(24) |
| 150 | + } |
| 151 | + |
| 152 | + userReviewTextView.snp.makeConstraints { make in |
| 153 | + make.top.equalTo(rateView.snp.bottom).offset(40) |
| 154 | + make.leading.equalToSuperview().offset(16) |
| 155 | + make.trailing.equalToSuperview().offset(-16) |
| 156 | + make.height.equalTo(181) |
| 157 | + } |
| 158 | + |
| 159 | + maximumWordLabel.snp.makeConstraints { make in |
| 160 | + make.top.equalTo(userReviewTextView.snp.bottom).offset(7) |
| 161 | + make.trailing.equalTo(userReviewTextView) |
| 162 | + } |
| 163 | + |
| 164 | + selectImageButton.snp.makeConstraints { |
| 165 | + $0.top.equalTo(maximumWordLabel.snp.bottom).offset(15) |
| 166 | + $0.leading.equalToSuperview().offset(15) |
| 167 | + $0.width.equalTo(60) |
| 168 | + $0.height.equalTo(60) |
| 169 | + } |
| 170 | + |
| 171 | + userReviewImageView.snp.makeConstraints { |
| 172 | + $0.top.equalTo(maximumWordLabel.snp.bottom).offset(15) |
| 173 | + $0.leading.equalTo(selectImageButton.snp.trailing).offset(13) |
| 174 | + $0.width.equalTo(60) |
| 175 | + $0.height.equalTo(60) |
| 176 | + } |
| 177 | + |
| 178 | + deleteMethodLabel.snp.makeConstraints { |
| 179 | + $0.top.equalTo(selectImageButton.snp.bottom).offset(7) |
| 180 | + $0.leading.equalTo(selectImageButton) |
| 181 | + } |
| 182 | + } |
| 183 | + |
| 184 | + override func setButtonEvent() { |
| 185 | + nextButton.addTarget(self, action: #selector(tappedNextButton), for: .touchUpInside) |
| 186 | + } |
| 187 | + |
| 188 | + @objc |
| 189 | + func didSelectedImage() { |
| 190 | + present(imagePickerController, animated: true, completion: nil) |
| 191 | + } |
| 192 | + |
| 193 | + @objc |
| 194 | + func didTappedimageView() { |
| 195 | + userReviewImageView.image = nil // 이미지 삭제 |
| 196 | + userPickedImage = nil |
| 197 | + } |
| 198 | + |
| 199 | + @objc |
| 200 | + func tappedNextButton() { |
| 201 | + |
| 202 | + } |
| 203 | + |
| 204 | + func setDelegate() { |
| 205 | + imagePickerController.delegate = self |
| 206 | + imagePickerController.sourceType = .photoLibrary |
| 207 | + imagePickerController.allowsEditing = false |
| 208 | + } |
| 209 | + |
| 210 | +// private func prepareForNextReview() { |
| 211 | +// let setRateVC = SetRateViewController() |
| 212 | +// setRateVC.dataBind(list: selectedList, |
| 213 | +// idList: selectedIDList, |
| 214 | +// reviewList: reviewList, |
| 215 | +// currentPage: currentPage + 1) |
| 216 | +// navigationController?.pushViewController(setRateVC, animated: true) |
| 217 | +// } |
| 218 | + |
| 219 | +} |
| 220 | + |
| 221 | +// MARK: - UIImagePickerControllerDelegate |
| 222 | + |
| 223 | +extension WritingReviewModalViewController: UIImagePickerControllerDelegate { |
| 224 | + func imagePickerController(_ picker: UIImagePickerController, didFinishPickingMediaWithInfo info: [UIImagePickerController.InfoKey: Any]) { |
| 225 | + if let image = info[UIImagePickerController.InfoKey.originalImage] as? UIImage { |
| 226 | + userReviewImageView.image = image |
| 227 | + userPickedImage = image |
| 228 | + } |
| 229 | + picker.dismiss(animated: true, completion: nil) |
| 230 | + } |
| 231 | +} |
| 232 | + |
| 233 | +// MARK: - UINavigationControllerDelegate |
| 234 | + |
| 235 | +extension WritingReviewModalViewController: UINavigationControllerDelegate { |
| 236 | +// func navigationController(_: UINavigationController, willShow viewController: UIViewController, animated _: Bool) { |
| 237 | +// if viewController == self { |
| 238 | +// // Pop 되기 직전의 로직을 여기서 실행 |
| 239 | +// print("Back button pressed, will pop the current view controller") |
| 240 | +// } |
| 241 | +// } |
| 242 | + |
| 243 | + // 키보드가 나타났다는 알림을 받으면 실행할 메서드 |
| 244 | + @objc |
| 245 | + func keyboardWillShow(_ noti: NSNotification) { |
| 246 | + // 키보드의 높이만큼 화면을 올려준다. |
| 247 | + if let keyboardFrame: NSValue = noti.userInfo?[UIResponder.keyboardFrameEndUserInfoKey] as? NSValue { |
| 248 | + let keyboardRectangle = keyboardFrame.cgRectValue |
| 249 | + UIView.animate( |
| 250 | + withDuration: 0.3, |
| 251 | + animations: { |
| 252 | + self.view.transform = CGAffineTransform(translationX: 0, y: -keyboardRectangle.height) |
| 253 | + self.navigationController?.isNavigationBarHidden = true |
| 254 | + } |
| 255 | + ) |
| 256 | + } |
| 257 | + } |
| 258 | + |
| 259 | + // 키보드가 사라졌다는 알림을 받으면 실행할 메서드 |
| 260 | + @objc |
| 261 | + func keyboardWillHide(_: NSNotification) { |
| 262 | + view.transform = .identity |
| 263 | + navigationController?.isNavigationBarHidden = false |
| 264 | + } |
| 265 | + |
| 266 | + // 노티피케이션을 추가하는 메서드 |
| 267 | + func addKeyboardNotifications() { |
| 268 | + // 키보드가 나타날 때 앱에게 알리는 메서드 추가 |
| 269 | + NotificationCenter.default.addObserver(self, |
| 270 | + selector: #selector(keyboardWillShow(_:)), |
| 271 | + name: UIResponder.keyboardWillShowNotification, |
| 272 | + object: nil) |
| 273 | + // 키보드가 사라질 때 앱에게 알리는 메서드 추가 |
| 274 | + NotificationCenter.default.addObserver(self, selector: #selector(keyboardWillHide(_:)), |
| 275 | + name: UIResponder.keyboardWillHideNotification, |
| 276 | + object: nil) |
| 277 | + } |
| 278 | + |
| 279 | + // 노티피케이션을 제거하는 메서드 |
| 280 | + func removeKeyboardNotifications() { |
| 281 | + // 키보드가 나타날 때 앱에게 알리는 메서드 제거 |
| 282 | + NotificationCenter.default.removeObserver(self, |
| 283 | + name: UIResponder.keyboardWillShowNotification, |
| 284 | + object: nil) |
| 285 | + // 키보드가 사라질 때 앱에게 알리는 메서드 제거 |
| 286 | + NotificationCenter.default.removeObserver(self, |
| 287 | + name: UIResponder.keyboardWillHideNotification, |
| 288 | + object: nil) |
| 289 | + } |
| 290 | +} |
| 291 | + |
| 292 | +#if DEBUG |
| 293 | +import SwiftUI |
| 294 | + |
| 295 | +struct aPreview: PreviewProvider { |
| 296 | + static var previews: some View { |
| 297 | + WritingReviewModalViewController().toPreview() |
| 298 | + } |
| 299 | +} |
| 300 | +#endif |
0 commit comments