import SwiftUI struct CreatorChannelFanTalkWriteView: View { @StateObject private var viewModel: CreatorChannelFanTalkWriteViewModel @FocusState private var isFocused: Bool let onSuccess: () -> Void init( creatorId: Int, mode: CreatorChannelFanTalkWriteViewModel.Mode, onSuccess: @escaping () -> Void ) { _viewModel = StateObject(wrappedValue: CreatorChannelFanTalkWriteViewModel(creatorId: creatorId, mode: mode)) self.onSuccess = onSuccess } var body: some View { BaseView(isLoading: $viewModel.isLoading) { ZStack(alignment: .bottom) { Color.black .ignoresSafeArea() .onTapGesture { hideKeyboard() } VStack(spacing: 0) { navigationBar TextEditor(text: $viewModel.content) .appFont(size: 16, weight: .regular) .foregroundColor(Color.white) .accentColor(Color.soda400) .scrollContentBackground(.hidden) .background(Color.black) .focused($isFocused) .padding(.horizontal, SodaSpacing.s14) .padding(.top, SodaSpacing.s20) .padding(.bottom, 52) } characterCountBar } .navigationBarBackButtonHidden(true) .onAppear { DispatchQueue.main.asyncAfter(deadline: .now() + 0.3) { isFocused = true } } .overlay(exitModal) .sodaToast(isPresented: $viewModel.isShowPopup, message: viewModel.errorMessage, autohideIn: 1) } } private var navigationBar: some View { HStack(spacing: 0) { Button(action: cancel) { Text(I18n.Common.cancel) .appFont(size: 16, weight: .regular) .foregroundColor(Color.white) .frame(width: 64, height: 56, alignment: .leading) } .buttonStyle(.plain) Spacer() Button(action: submit) { Text(I18n.CreatorChannelFanTalk.send) .appFont(size: 16, weight: .medium) .foregroundColor(Color.white) .padding(.horizontal, SodaSpacing.s12) .frame(height: 44) .background(viewModel.canSend ? Color.soda400 : Color.gray800) .clipShape(Capsule()) } .buttonStyle(.plain) .disabled(viewModel.canSend == false) } .padding(.horizontal, SodaSpacing.s14) .frame(height: 56) .background(Color.black) } private var characterCountBar: some View { HStack(spacing: 0) { Spacer() Text("\(viewModel.content.count)") .appFont(size: 16, weight: .medium) .foregroundColor(Color.white) Text("/\(viewModel.maxContentCount)자") .appFont(size: 16, weight: .medium) .foregroundColor(Color.gray500) } .padding(.horizontal, SodaSpacing.s14) .frame(height: 52) .background(Color.black) .overlay(alignment: .top) { Rectangle() .fill(Color.gray700) .frame(height: 1) } } @ViewBuilder private var exitModal: some View { if viewModel.shouldShowExitModal { SodaV2ActionModal( title: I18n.CreatorChannelFanTalk.exitModalTitle, message: I18n.CreatorChannelFanTalk.exitModalMessage, button1: SodaV2ActionModalButton( label: I18n.CreatorChannelFanTalk.exitModalContinue, action: { viewModel.shouldShowExitModal = false } ), button2: SodaV2ActionModalButton( label: I18n.CreatorChannelFanTalk.exitModalExit, action: { viewModel.shouldShowExitModal = false AppState.shared.back() } ), onDimmedTap: { viewModel.shouldShowExitModal = false } ) } } private func cancel() { hideKeyboard() if viewModel.handleCancel() { AppState.shared.back() } } private func submit() { hideKeyboard() viewModel.submit { AppState.shared.back() DispatchQueue.main.async { onSuccess() } } } }