라이브 - 공지 영역 너비가 넘어가는 현상 수정
This commit is contained in:
		| @@ -12,6 +12,7 @@ import PopupView | ||||
| struct LiveRoomView: View { | ||||
|     @State private var isShowingNewChat = false | ||||
|     @State private var isShowPhotoPicker = false | ||||
|     @State private var noticeViewHeight: CGFloat = UIFont.systemFontSize | ||||
|      | ||||
|     let columns = [ | ||||
|         GridItem(.flexible()), | ||||
| @@ -47,6 +48,7 @@ struct LiveRoomView: View { | ||||
|                                 .stroke(Color(hex: "ff5c49"), lineWidth: 1) | ||||
|                         ) | ||||
|                         .onTapGesture { | ||||
|                             viewModel.isExpandNotice = false | ||||
|                             if let liveRoomInfo = viewModel.liveRoomInfo, liveRoomInfo.creatorId == UserDefaults.int(forKey: .userId) { | ||||
|                                 viewModel.isShowLiveEndPopup = true | ||||
|                             } else { | ||||
| @@ -166,15 +168,31 @@ struct LiveRoomView: View { | ||||
|                                 Text("[공지]") | ||||
|                                     .font(.custom(Font.bold.rawValue, size: 11.3)) | ||||
|                                     .foregroundColor(.white) | ||||
|                                     .onTapGesture { | ||||
|                                         viewModel.isExpandNotice.toggle() | ||||
|                                     } | ||||
|                                  | ||||
|                                 AttributedTextView( | ||||
|                                     attributedString: makeAttributedString(liveRoomInfo.notice), | ||||
|                                     lineLimit: viewModel.isExpandNotice ? Int.max : 1 | ||||
|                                 ) { | ||||
|                                     UIApplication.shared.open($0) | ||||
|                                 if viewModel.isExpandNotice { | ||||
|                                     VStack(spacing: 10) { | ||||
|                                         TextView(text: liveRoomInfo.notice, dynamicHeight: $noticeViewHeight) | ||||
|                                             .frame(height: viewModel.isExpandNotice ? noticeViewHeight : UIFont.systemFontSize) | ||||
|                                          | ||||
|                                         Text("닫기") | ||||
|                                             .font(.custom(Font.light.rawValue, size: 11.3)) | ||||
|                                             .foregroundColor(.white) | ||||
|                                             .onTapGesture { | ||||
|                                                 viewModel.isExpandNotice = false | ||||
|                                             } | ||||
|                                     } | ||||
|                                 } else { | ||||
|                                     Text(liveRoomInfo.notice) | ||||
|                                         .font(.custom(Font.light.rawValue, size: 11.3)) | ||||
|                                         .foregroundColor(.white) | ||||
|                                         .lineLimit(1) | ||||
|                                         .onTapGesture { | ||||
|                                             viewModel.isExpandNotice = true | ||||
|                                         } | ||||
|                                 } | ||||
|                                 .fixedSize(horizontal: false, vertical: true) | ||||
|                                 .lineSpacing(6) | ||||
|                             } | ||||
|                             .padding(.horizontal, 26.7) | ||||
|                             .padding(.vertical, 13.3) | ||||
| @@ -182,9 +200,6 @@ struct LiveRoomView: View { | ||||
|                             .background(Color(hex: "3d2a6c")) | ||||
|                             .padding(.top, 10) | ||||
|                             .contentShape(Rectangle()) | ||||
|                             .onTapGesture { | ||||
|                                 viewModel.isExpandNotice.toggle() | ||||
|                             } | ||||
|                         } | ||||
|                          | ||||
|                         if !viewModel.isSpeakerFold { | ||||
| @@ -914,71 +929,49 @@ struct LiveRoomView_Previews: PreviewProvider { | ||||
|     } | ||||
| } | ||||
|  | ||||
| struct AttributedTextView: UIViewRepresentable { | ||||
|     let attributedString: NSAttributedString | ||||
|     let lineLimit: Int | ||||
|     let onURLTapped: (URL) -> Void | ||||
|      | ||||
| struct TextView: UIViewRepresentable { | ||||
|     var text: String | ||||
|     @Binding var dynamicHeight: CGFloat | ||||
|      | ||||
|     func makeUIView(context: Context) -> UITextView { | ||||
|         let textView = UITextView() | ||||
|         textView.text = text | ||||
|         textView.isEditable = false | ||||
|         textView.isSelectable = false | ||||
|         textView.isScrollEnabled = false | ||||
|         textView.isScrollEnabled = true | ||||
|         textView.backgroundColor = .clear | ||||
|         textView.dataDetectorTypes = .link | ||||
|         textView.font = UIFont(name: Font.light.rawValue, size: 11.3) | ||||
|         textView.textColor = .white | ||||
|         textView.textContainer.lineFragmentPadding = 0 | ||||
|         textView.textContainerInset = .zero | ||||
|         textView.textContainer.maximumNumberOfLines = lineLimit | ||||
|         textView.textContainer.lineBreakMode = lineLimit == 1 ? .byTruncatingTail : .byWordWrapping | ||||
|         textView.delegate = context.coordinator | ||||
|          | ||||
|         textView.isUserInteractionEnabled = true | ||||
|          | ||||
|         // Add tap gesture recognizer to handle URL tap events | ||||
|         let tapGestureRecognizer = UITapGestureRecognizer(target: context.coordinator, action: #selector(Coordinator.handleTapGesture(_:))) | ||||
|         textView.addGestureRecognizer(tapGestureRecognizer) | ||||
|  | ||||
|          | ||||
|         return textView | ||||
|     } | ||||
|      | ||||
|     func updateUIView(_ uiView: UITextView, context: Context) { | ||||
|         uiView.attributedText = attributedString | ||||
|         uiView.textColor = UIColor.white | ||||
|         uiView.textContainer.maximumNumberOfLines = lineLimit | ||||
|         uiView.textContainer.lineBreakMode = lineLimit == 1 ? .byTruncatingTail : .byWordWrapping | ||||
|         uiView.text = text | ||||
|         DispatchQueue.main.async { | ||||
|             let height = uiView.sizeThatFits(uiView.frame.size).height | ||||
|             self.dynamicHeight = height > 500 ? 500 : height | ||||
|         } | ||||
|     } | ||||
|      | ||||
|     func makeCoordinator() -> Coordinator { | ||||
|         Coordinator(onURLTapped: onURLTapped) | ||||
|         Coordinator($dynamicHeight) | ||||
|     } | ||||
|      | ||||
|     class Coordinator: NSObject, UITextViewDelegate { | ||||
|         let onURLTapped: (URL) -> Void | ||||
|         let linkAttributeName = NSAttributedString.Key.link.rawValue | ||||
|         var dynamicHeight: Binding<CGFloat> | ||||
|          | ||||
|         init(onURLTapped: @escaping (URL) -> Void) { | ||||
|             self.onURLTapped = onURLTapped | ||||
|         init(_ dynamicHeight: Binding<CGFloat>) { | ||||
|             self.dynamicHeight = dynamicHeight | ||||
|         } | ||||
|          | ||||
|         @objc func handleTapGesture(_ gesture: UITapGestureRecognizer) { | ||||
|             let textView = gesture.view as? UITextView | ||||
|             let location = gesture.location(in: textView) | ||||
|              | ||||
|             let layoutManager = textView?.layoutManager | ||||
|             let characterIndex = layoutManager?.characterIndex(for: location, in: textView!.textContainer, fractionOfDistanceBetweenInsertionPoints: nil) | ||||
|              | ||||
|             if characterIndex != NSNotFound { | ||||
|                 let attributedString = textView?.attributedText | ||||
|                  | ||||
|                 attributedString?.enumerateAttribute(NSAttributedString.Key(rawValue: linkAttributeName), in: NSRange(location: 0, length: attributedString!.length), options: []) { value, range, _ in | ||||
|                     if let url = value as? URL, NSLocationInRange(characterIndex!, range) { | ||||
|                         onURLTapped(url) | ||||
|                     } | ||||
|                 } | ||||
|         func textViewDidChange(_ textView: UITextView) { | ||||
|             DispatchQueue.main.async { | ||||
|                 self.dynamicHeight.wrappedValue = textView.sizeThatFits(textView.frame.size).height | ||||
|             } | ||||
|         } | ||||
|     } | ||||
| } | ||||
|  | ||||
|   | ||||
		Reference in New Issue
	
	Block a user
	 Yu Sung
					Yu Sung